提交文件
This commit is contained in:
493
.qoder/repowiki/zh/content/数据模型详解/关系映射说明.md
Normal file
493
.qoder/repowiki/zh/content/数据模型详解/关系映射说明.md
Normal file
@@ -0,0 +1,493 @@
|
||||
# 关系映射说明
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [finance.py](file://backend/app/models/finance.py)
|
||||
- [database.py](file://backend/app/core/database.py)
|
||||
- [config.py](file://backend/app/core/config.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [department_service.py](file://backend/app/services/department_service.py)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py)
|
||||
- [database.md](file://docs/database.md)
|
||||
- [backend.md](file://docs/backend.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
本文件详细说明医院绩效管理系统的数据模型关系映射设计。系统采用SQLAlchemy ORM实现,涵盖科室层级结构、员工与科室关系、考核记录与明细关系等复杂业务场景。重点解释一对一、一对多、多对多关系的实现方式,包括外键约束、级联删除、反向关系和懒加载机制。
|
||||
|
||||
## 项目结构
|
||||
|
||||
系统采用分层架构,核心模型位于`backend/app/models/`目录,数据库配置在`backend/app/core/`目录,服务层在`backend/app/services/`目录,API路由在`backend/app/api/v1/`目录。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "数据模型层"
|
||||
A[models.py<br/>核心业务模型]
|
||||
B[finance.py<br/>财务模型]
|
||||
C[__init__.py<br/>模型导出]
|
||||
end
|
||||
subgraph "核心配置层"
|
||||
D[database.py<br/>数据库连接]
|
||||
E[config.py<br/>系统配置]
|
||||
end
|
||||
subgraph "服务层"
|
||||
F[staff_service.py<br/>员工服务]
|
||||
G[assessment_service.py<br/>考核服务]
|
||||
H[department_service.py<br/>科室服务]
|
||||
end
|
||||
subgraph "API层"
|
||||
I[departments.py<br/>科室API]
|
||||
J[assessments.py<br/>考核API]
|
||||
end
|
||||
A --> D
|
||||
B --> D
|
||||
F --> A
|
||||
G --> A
|
||||
H --> A
|
||||
I --> H
|
||||
J --> G
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L263)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
|
||||
## 核心组件
|
||||
|
||||
系统包含以下核心数据模型:
|
||||
|
||||
### 基础模型
|
||||
- **Base**: SQLAlchemy DeclarativeBase基类
|
||||
- **异步数据库引擎**: 基于asyncpg的异步连接
|
||||
- **会话管理**: 自动事务管理和连接池配置
|
||||
|
||||
### 业务模型
|
||||
- **Department**: 科室信息,支持自关联
|
||||
- **Staff**: 员工信息,一对多关联科室
|
||||
- **Assessment**: 考核记录,一对多关联员工
|
||||
- **AssessmentDetail**: 考核明细,多对多中间表
|
||||
- **Indicator**: 考核指标,支持BSC维度
|
||||
- **SalaryRecord**: 工资核算记录
|
||||
- **User**: 系统用户,关联员工
|
||||
- **PerformancePlan**: 绩效计划,支持层级结构
|
||||
- **PlanKpiRelation**: 计划指标关联
|
||||
- **IndicatorTemplate**: 指标模板
|
||||
- **TemplateIndicator**: 模板指标关联
|
||||
- **DepartmentFinance**: 科室财务记录
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L438)
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L79)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用经典的三层架构模式,通过ORM模型实现业务逻辑与数据持久化的分离。
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
DEPARTMENTS ||--o{ STAFF : "一对多"
|
||||
STAFF ||--o{ ASSESSMENTS : "一对多"
|
||||
ASSESSMENTS ||--o{ ASSESSMENT_DETAILS : "一对多"
|
||||
INDICATORS ||--o{ ASSESSMENT_DETAILS : "一对多"
|
||||
STAFF ||--o{ SALARY_RECORDS : "一对多"
|
||||
DEPARTMENTS ||--o{ DEPARTMENT_FINANCES : "一对多"
|
||||
USERS ||--|| STAFF : "一对一"
|
||||
PERFORMANCE_PLANS ||--o{ PLAN_KPI_RELATIONS : "一对多"
|
||||
INDICATORS ||--o{ PLAN_KPI_RELATIONS : "一对多"
|
||||
INDICATOR_TEMPLATES ||--o{ TEMPLATE_INDICATORS : "一对多"
|
||||
INDICATORS ||--o{ TEMPLATE_INDICATORS : "一对多"
|
||||
DEPARTMENTS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
enum dept_type
|
||||
int parent_id FK
|
||||
int level
|
||||
int sort_order
|
||||
boolean is_active
|
||||
}
|
||||
STAFF {
|
||||
int id PK
|
||||
string employee_id UK
|
||||
string name
|
||||
int department_id FK
|
||||
string position
|
||||
string title
|
||||
float base_salary
|
||||
float performance_ratio
|
||||
enum status
|
||||
}
|
||||
ASSESSMENTS {
|
||||
int id PK
|
||||
int staff_id FK
|
||||
int period_year
|
||||
int period_month
|
||||
enum status
|
||||
float total_score
|
||||
float weighted_score
|
||||
}
|
||||
ASSESSMENT_DETAILS {
|
||||
int id PK
|
||||
int assessment_id FK
|
||||
int indicator_id FK
|
||||
float actual_value
|
||||
float score
|
||||
}
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string code UK
|
||||
enum indicator_type
|
||||
enum bs_dimension
|
||||
float weight
|
||||
float max_score
|
||||
}
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L438)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L22-L183)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 科室层级结构关系
|
||||
|
||||
科室模型实现了完整的自关联关系,支持多层级的组织架构。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+DeptType dept_type
|
||||
+int parent_id
|
||||
+int level
|
||||
+int sort_order
|
||||
+boolean is_active
|
||||
+Department parent
|
||||
+Department[] children
|
||||
+Staff[] staff
|
||||
}
|
||||
Department "1" <-- "0..*" Department : "parent"
|
||||
Department "1" --> "0..*" Department : "children"
|
||||
Department "1" --> "0..*" Staff : "staff"
|
||||
```
|
||||
|
||||
**实现特点**:
|
||||
- 使用`remote_side`参数解决自关联的歧义性
|
||||
- 通过`backref="children"`实现反向关系
|
||||
- 支持多层级嵌套结构
|
||||
- 通过`level`字段维护层级深度
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
|
||||
### 员工与科室关系
|
||||
|
||||
员工与科室之间是一对多的关系,通过外键约束保证数据完整性。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as "客户端"
|
||||
participant API as "部门API"
|
||||
participant Service as "DepartmentService"
|
||||
participant DB as "数据库"
|
||||
Client->>API : GET /api/v1/departments/tree
|
||||
API->>Service : get_tree(dept_type)
|
||||
Service->>DB : SELECT * FROM departments ORDER BY sort_order, id
|
||||
DB-->>Service : 部门列表
|
||||
Service->>Service : 构建树形结构
|
||||
Service-->>API : 树形结构数据
|
||||
API-->>Client : 返回科室树
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L43-L51)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L126)
|
||||
|
||||
**实现特点**:
|
||||
- 使用`selectinload`优化N+1查询问题
|
||||
- 支持按科室类型过滤
|
||||
- 手动构建树形结构避免懒加载问题
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L114)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L126)
|
||||
|
||||
### 考核记录与明细关系
|
||||
|
||||
考核系统采用主从结构,支持复杂的多对多关系。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+AssessmentStatus status
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentDetail[] details
|
||||
+Staff staff
|
||||
}
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+Indicator indicator
|
||||
+Assessment assessment
|
||||
}
|
||||
class Indicator {
|
||||
+int id
|
||||
+string code
|
||||
+IndicatorType indicator_type
|
||||
+float weight
|
||||
+AssessmentDetail[] assessment_details
|
||||
}
|
||||
Assessment "1" --> "0..*" AssessmentDetail : "details"
|
||||
AssessmentDetail "1" --> "1" Staff : "staff"
|
||||
AssessmentDetail "1" --> "1" Indicator : "indicator"
|
||||
Indicator "1" --> "0..*" AssessmentDetail : "assessment_details"
|
||||
```
|
||||
|
||||
**实现特点**:
|
||||
- 使用`cascade="all, delete-orphan"`实现级联删除
|
||||
- 通过`foreign_keys`参数区分多重外键关系
|
||||
- 支持复杂的统计计算(总分、加权得分)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L202)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
|
||||
### 财务核算关系
|
||||
|
||||
财务模块与科室建立了清晰的一对多关系。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([财务记录创建]) --> Validate["验证科室存在性"]
|
||||
Validate --> CreateRecord["创建财务记录"]
|
||||
CreateRecord --> Save["保存到数据库"]
|
||||
Save --> LoadDept["加载科室信息"]
|
||||
LoadDept --> Return["返回完整记录"]
|
||||
Validate --> |验证失败| Error["返回错误"]
|
||||
Error --> End([结束])
|
||||
Return --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L79)
|
||||
|
||||
**实现特点**:
|
||||
- 使用`backref="finances"`简化反向访问
|
||||
- 通过枚举类型管理财务类别
|
||||
- 实现金额正数约束
|
||||
|
||||
**章节来源**
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L79)
|
||||
|
||||
### 指标模板关系
|
||||
|
||||
指标模板系统支持复杂的多对多关系。
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
INDICATOR_TEMPLATES ||--o{ TEMPLATE_INDICATORS : "一对多"
|
||||
INDICATORS ||--o{ TEMPLATE_INDICATORS : "一对多"
|
||||
INDICATOR_TEMPLATES {
|
||||
int id PK
|
||||
string template_code UK
|
||||
enum template_type
|
||||
boolean is_active
|
||||
}
|
||||
TEMPLATE_INDICATORS {
|
||||
int id PK
|
||||
int template_id FK
|
||||
int indicator_id FK
|
||||
float weight
|
||||
int sort_order
|
||||
}
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string code UK
|
||||
enum indicator_type
|
||||
enum bs_dimension
|
||||
float weight
|
||||
}
|
||||
```
|
||||
|
||||
**实现特点**:
|
||||
- 使用复合唯一索引防止重复关联
|
||||
- 支持模板级别的权重管理
|
||||
- 提供排序字段支持显示顺序
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L387-L438)
|
||||
|
||||
## 依赖分析
|
||||
|
||||
系统采用模块化设计,各层之间依赖关系清晰。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "外部依赖"
|
||||
A[SQLAlchemy]
|
||||
B[FastAPI]
|
||||
C[Alembic]
|
||||
D[asyncpg]
|
||||
end
|
||||
subgraph "核心模块"
|
||||
E[database.py]
|
||||
F[models.py]
|
||||
G[finance.py]
|
||||
end
|
||||
subgraph "业务模块"
|
||||
H[staff_service.py]
|
||||
I[assessment_service.py]
|
||||
J[department_service.py]
|
||||
end
|
||||
subgraph "接口模块"
|
||||
K[departments.py]
|
||||
L[assessments.py]
|
||||
end
|
||||
A --> E
|
||||
B --> K
|
||||
B --> L
|
||||
C --> F
|
||||
D --> E
|
||||
E --> F
|
||||
E --> G
|
||||
F --> H
|
||||
F --> I
|
||||
F --> J
|
||||
H --> K
|
||||
I --> L
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L1-L11)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L11)
|
||||
|
||||
**依赖特性**:
|
||||
- 异步数据库连接支持高并发
|
||||
- 模块化导入避免循环依赖
|
||||
- 明确的层次边界确保代码可维护性
|
||||
|
||||
**章节来源**
|
||||
- [config.py](file://backend/app/core/config.py#L18-L26)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 查询优化策略
|
||||
|
||||
1. **懒加载与急加载选择**
|
||||
- 使用`selectinload`避免N+1查询问题
|
||||
- 在API层根据需要选择性加载关联数据
|
||||
|
||||
2. **索引优化**
|
||||
- 为常用查询字段建立索引
|
||||
- 使用复合索引支持多条件查询
|
||||
|
||||
3. **连接池配置**
|
||||
- 配置合适的连接池大小
|
||||
- 设置超时和重试机制
|
||||
|
||||
### 关系查询最佳实践
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始查询]) --> Choose["选择查询策略"]
|
||||
Choose --> |简单查询| Lazy["使用懒加载"]
|
||||
Choose --> |复杂查询| Eager["使用急加载"]
|
||||
Lazy --> Check["检查N+1问题"]
|
||||
Check --> |存在| Fix["修复为急加载"]
|
||||
Check --> |不存在| Optimize["优化查询"]
|
||||
Eager --> Selective["选择性加载"]
|
||||
Selective --> Filter["应用过滤条件"]
|
||||
Filter --> Result["返回结果"]
|
||||
Optimize --> Result
|
||||
Fix --> Result
|
||||
```
|
||||
|
||||
**优化建议**:
|
||||
- 对于API响应,优先使用急加载确保一次性获取所需数据
|
||||
- 对于后台任务,使用懒加载减少内存占用
|
||||
- 合理使用索引提高查询性能
|
||||
- 避免不必要的关联查询
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见关系问题
|
||||
|
||||
1. **循环依赖问题**
|
||||
```python
|
||||
# 解决方案:延迟导入
|
||||
from app.models.models import Department # 在文件末尾导入
|
||||
```
|
||||
|
||||
2. **自关联关系冲突**
|
||||
```python
|
||||
# 解决方案:使用remote_side参数
|
||||
parent: Mapped[Optional["Department"]] = relationship("Department", remote_side=[id], backref="children")
|
||||
```
|
||||
|
||||
3. **多重外键关系**
|
||||
```python
|
||||
# 解决方案:明确指定foreign_keys
|
||||
assessor: Mapped[Optional["Staff"]] = relationship("Staff", foreign_keys=[assessor_id])
|
||||
reviewer: Mapped[Optional["Staff"]] = relationship("Staff", foreign_keys=[reviewer_id])
|
||||
```
|
||||
|
||||
### 数据一致性保证
|
||||
|
||||
1. **外键约束检查**
|
||||
- 确保引用的记录存在
|
||||
- 验证级联删除行为
|
||||
|
||||
2. **事务管理**
|
||||
- 使用异步事务确保原子性
|
||||
- 合理的回滚策略
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L169-L173)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L117-L118)
|
||||
|
||||
## 结论
|
||||
|
||||
本系统通过精心设计的数据模型关系映射,成功实现了复杂的医院绩效管理业务需求。主要特点包括:
|
||||
|
||||
1. **清晰的关系设计**:通过一对一、一对多、多对多关系准确反映业务实体间的联系
|
||||
2. **完善的约束机制**:外键约束、检查约束确保数据完整性
|
||||
3. **灵活的查询策略**:结合懒加载和急加载满足不同场景需求
|
||||
4. **可扩展的架构**:模块化设计支持功能扩展和维护
|
||||
|
||||
系统在保证数据一致性的前提下,提供了良好的性能表现和可维护性,为医院绩效管理提供了坚实的技术基础。
|
||||
576
.qoder/repowiki/zh/content/数据模型详解/数据库约束设计.md
Normal file
576
.qoder/repowiki/zh/content/数据模型详解/数据库约束设计.md
Normal file
@@ -0,0 +1,576 @@
|
||||
# 数据库约束设计
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [finance.py](file://backend/app/models/finance.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
- [database.py](file://backend/app/core/database.py)
|
||||
- [config.py](file://backend/app/core/config.py)
|
||||
- [database.md](file://docs/database.md)
|
||||
- [main.py](file://backend/app/main.py)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
本文件详细阐述了医院绩效管理系统的数据库约束设计,涵盖唯一性约束、检查约束、索引设计和外键约束的实现原理与业务意义。通过对系统中各个数据表的约束策略进行深入分析,帮助开发者和运维人员理解数据完整性保障机制,并提供针对约束冲突的处理策略和优化建议。
|
||||
|
||||
## 项目结构
|
||||
|
||||
该系统采用基于 SQLAlchemy 的 ORM 设计,数据库约束主要通过以下方式实现:
|
||||
- 数据模型层定义:在模型类中直接声明约束和索引
|
||||
- 迁移脚本层:通过 Alembic 版本化管理数据库结构变更
|
||||
- 配置层:数据库连接和会话管理
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "数据模型层"
|
||||
Models[ORM 模型定义]
|
||||
Constraints[约束声明]
|
||||
Indexes[索引定义]
|
||||
end
|
||||
subgraph "迁移管理层"
|
||||
Alembic[Alembic 迁移]
|
||||
Initial[初始版本]
|
||||
Template[模板版本]
|
||||
end
|
||||
subgraph "配置层"
|
||||
Config[数据库配置]
|
||||
Engine[异步引擎]
|
||||
Session[会话管理]
|
||||
end
|
||||
Models --> Alembic
|
||||
Constraints --> Alembic
|
||||
Indexes --> Alembic
|
||||
Alembic --> Initial
|
||||
Alembic --> Template
|
||||
Config --> Engine
|
||||
Engine --> Session
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L22-L84)
|
||||
- [database.py](file://backend/app/core/database.py#L10-L20)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L50)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L1-L20)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
|
||||
## 核心组件
|
||||
|
||||
系统的核心数据模型包括科室、员工、考核指标、考核记录、工资记录等关键实体。每个实体都配备了相应的约束策略以确保数据完整性。
|
||||
|
||||
### 主要数据实体
|
||||
|
||||
| 实体名称 | 主键字段 | 唯一约束 | 外键约束 | 检查约束 |
|
||||
|---------|---------|---------|---------|---------|
|
||||
| departments | id | code | 无 | 无 |
|
||||
| staff | id | employee_id | department_id | 无 |
|
||||
| indicators | id | code | 无 | weight > 0 |
|
||||
| assessments | id | 无 | staff_id, assessor_id, reviewer_id | 无 |
|
||||
| assessment_details | id | 无 | assessment_id, indicator_id | 无 |
|
||||
| salary_records | id | 无 | staff_id | 无 |
|
||||
| users | id | username | staff_id | 无 |
|
||||
| performance_plans | id | plan_code | department_id, staff_id, parent_plan_id, submitter_id, approver_id | 无 |
|
||||
| plan_kpi_relations | id | (plan_id, indicator_id) 唯一 | plan_id, indicator_id | 无 |
|
||||
| indicator_templates | id | template_code | 无 | 无 |
|
||||
| template_indicators | id | (template_id, indicator_id) 唯一 | template_id, indicator_id | 无 |
|
||||
| department_finances | id | 无 | department_id | amount >= 0 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L437)
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用三层约束设计架构:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "约束层次"
|
||||
Layer1[业务层约束<br/>模型定义]
|
||||
Layer2[持久层约束<br/>数据库层面]
|
||||
Layer3[应用层约束<br/>应用程序逻辑]
|
||||
end
|
||||
subgraph "约束类型"
|
||||
Unique[唯一性约束]
|
||||
Check[检查约束]
|
||||
FK[外键约束]
|
||||
Index[索引约束]
|
||||
end
|
||||
subgraph "应用场景"
|
||||
Business[业务规则]
|
||||
DataIntegrity[数据完整性]
|
||||
QueryOptimization[查询优化]
|
||||
Referential[参照完整性]
|
||||
end
|
||||
Layer1 --> Unique
|
||||
Layer1 --> Check
|
||||
Layer1 --> FK
|
||||
Layer1 --> Index
|
||||
Unique --> Business
|
||||
Check --> DataIntegrity
|
||||
FK --> Referential
|
||||
Index --> QueryOptimization
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L68-L68)
|
||||
- [models.py](file://backend/app/models/models.py#L145-L145)
|
||||
- [finance.py](file://backend/app/models/finance.py#L73-L73)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 唯一性约束设计
|
||||
|
||||
唯一性约束是确保数据唯一性的基础机制,系统在多个关键字段上实施了唯一性约束。
|
||||
|
||||
#### 唯一性约束实现
|
||||
|
||||
| 表名 | 唯一字段 | 约束目的 | 业务意义 |
|
||||
|------|---------|---------|---------|
|
||||
| departments | code | 科室编码唯一性 | 防止重复科室标识,便于精确识别 |
|
||||
| staff | employee_id | 员工工号唯一性 | 确保员工身份唯一标识,避免重复录入 |
|
||||
| users | username | 用户名唯一性 | 保证系统用户身份唯一,防止登录冲突 |
|
||||
| indicators | code | 指标编码唯一性 | 确保考核指标的唯一标识,便于管理和查询 |
|
||||
| performance_plans | plan_code | 计划编码唯一性 | 防止重复计划标识,维护计划体系完整性 |
|
||||
| indicator_templates | template_code | 模板编码唯一性 | 确保模板的唯一标识,便于模板管理和复用 |
|
||||
| plan_kpi_relations | (plan_id, indicator_id) | 关联关系唯一性 | 防止重复关联,确保计划-指标关系的准确性 |
|
||||
| template_indicators | (template_id, indicator_id) | 关联关系唯一性 | 防止重复关联,确保模板-指标关系的准确性 |
|
||||
|
||||
#### 唯一性约束触发条件
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([数据插入/更新]) --> CheckUnique["检查唯一性约束"]
|
||||
CheckUnique --> UniqueExists{"是否存在重复值?"}
|
||||
UniqueExists --> |是| RaiseError["抛出唯一性约束异常"]
|
||||
UniqueExists --> |否| Continue["继续执行操作"]
|
||||
RaiseError --> HandleConflict["处理冲突"]
|
||||
HandleConflict --> Rollback["回滚事务"]
|
||||
Continue --> Commit["提交事务"]
|
||||
Rollback --> End([结束])
|
||||
Commit --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L37-L37)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L61-L61)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L36-L36)
|
||||
|
||||
**章节来源**
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L27-L28)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L46-L47)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L160-L160)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L27-L28)
|
||||
|
||||
### 检查约束设计
|
||||
|
||||
检查约束用于强制执行复杂的业务规则,确保数据符合预定义的条件。
|
||||
|
||||
#### 检查约束实现
|
||||
|
||||
| 表名 | 约束条件 | 约束名称 | 业务含义 |
|
||||
|------|---------|---------|---------|
|
||||
| indicators | weight > 0 | ck_indicator_weight | 确保指标权重必须为正数,保证计算逻辑正确性 |
|
||||
| department_finances | amount >= 0 | ck_finance_amount | 确保财务金额不能为负数,维护财务数据准确性 |
|
||||
|
||||
#### 检查约束验证流程
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as 客户端
|
||||
participant DB as 数据库
|
||||
participant Trigger as 检查约束触发器
|
||||
Client->>DB : INSERT/UPDATE 操作
|
||||
DB->>Trigger : 验证检查约束
|
||||
Trigger->>Trigger : 计算约束条件
|
||||
Trigger->>Trigger : 判断条件是否满足
|
||||
alt 条件满足
|
||||
Trigger->>DB : 允许操作
|
||||
DB-->>Client : 操作成功
|
||||
else 条件不满足
|
||||
Trigger->>DB : 拒绝操作
|
||||
DB-->>Client : 抛出检查约束异常
|
||||
end
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L145-L145)
|
||||
- [finance.py](file://backend/app/models/finance.py#L73-L73)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L143-L146)
|
||||
- [finance.py](file://backend/app/models/finance.py#L68-L74)
|
||||
|
||||
### 外键约束设计
|
||||
|
||||
外键约束确保参照完整性,防止出现孤立记录和无效引用。
|
||||
|
||||
#### 外键约束实现
|
||||
|
||||
| 表名 | 外键字段 | 引用表 | 约束类型 | 业务意义 |
|
||||
|------|---------|--------|---------|---------|
|
||||
| staff | department_id | departments | 必须引用有效科室 | 确保员工属于存在的科室 |
|
||||
| assessments | staff_id | staff | 必须引用有效员工 | 确保考核记录对应有效员工 |
|
||||
| assessments | assessor_id | staff | 可选引用有效员工 | 确保考核人存在且有效 |
|
||||
| assessments | reviewer_id | staff | 可选引用有效员工 | 确保审核人存在且有效 |
|
||||
| assessment_details | assessment_id | assessments | 必须引用有效考核记录 | 确保明细对应有效考核 |
|
||||
| assessment_details | indicator_id | indicators | 必须引用有效指标 | 确保明细对应有效指标 |
|
||||
| salary_records | staff_id | staff | 必须引用有效员工 | 确保工资记录对应有效员工 |
|
||||
| users | staff_id | staff | 可选引用有效员工 | 确保用户关联有效员工 |
|
||||
| performance_plans | department_id | departments | 可选引用有效科室 | 确保计划关联有效科室 |
|
||||
| performance_plans | staff_id | staff | 可选引用有效员工 | 确保计划关联有效员工 |
|
||||
| performance_plans | parent_plan_id | performance_plans | 自引用 | 确保计划层级关系正确 |
|
||||
| performance_plans | submitter_id | users | 可选引用有效用户 | 确保提交人存在且有效 |
|
||||
| performance_plans | approver_id | users | 可选引用有效用户 | 确保审批人存在且有效 |
|
||||
| plan_kpi_relations | plan_id | performance_plans | 必须引用有效计划 | 确保关联关系有效 |
|
||||
| plan_kpi_relations | indicator_id | indicators | 必须引用有效指标 | 确保关联关系有效 |
|
||||
| template_indicators | template_id | indicator_templates | 必须引用有效模板 | 确保关联关系有效 |
|
||||
| template_indicators | indicator_id | indicators | 必须引用有效指标 | 确保关联关系有效 |
|
||||
| department_finances | department_id | departments | 必须引用有效科室 | 确保财务记录对应有效科室 |
|
||||
|
||||
#### 外键约束级联行为
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+id : int
|
||||
+name : str
|
||||
+code : str
|
||||
+children : Department[]
|
||||
}
|
||||
class Staff {
|
||||
+id : int
|
||||
+employee_id : str
|
||||
+department_id : int
|
||||
+department : Department
|
||||
}
|
||||
class Assessment {
|
||||
+id : int
|
||||
+staff_id : int
|
||||
+staff : Staff
|
||||
+assessor_id : int
|
||||
+reviewer_id : int
|
||||
}
|
||||
class PerformancePlan {
|
||||
+id : int
|
||||
+department_id : int
|
||||
+staff_id : int
|
||||
+parent_plan_id : int
|
||||
+submitter_id : int
|
||||
+approver_id : int
|
||||
+parent_plan : PerformancePlan
|
||||
}
|
||||
Department --> Staff : "1 : N"
|
||||
Staff --> Assessment : "1 : N"
|
||||
PerformancePlan --> PerformancePlan : "self-ref"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L70-L70)
|
||||
- [models.py](file://backend/app/models/models.py#L154-L154)
|
||||
- [models.py](file://backend/app/models/models.py#L283-L283)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L95-L95)
|
||||
- [models.py](file://backend/app/models/models.py#L154-L154)
|
||||
- [models.py](file://backend/app/models/models.py#L281-L281)
|
||||
|
||||
### 索引设计策略
|
||||
|
||||
索引设计直接影响查询性能和数据检索效率,系统针对高频查询场景建立了多维索引。
|
||||
|
||||
#### 单列索引设计
|
||||
|
||||
| 表名 | 索引字段 | 索引名称 | 查询场景 | 性能收益 |
|
||||
|------|---------|---------|---------|---------|
|
||||
| departments | dept_type | idx_dept_type | 按科室类型查询 | 快速筛选特定类型科室 |
|
||||
| departments | parent_id | idx_dept_parent | 按上级科室查询 | 快速获取子科室层级 |
|
||||
| staff | department_id | idx_staff_dept | 按科室查询员工 | 快速定位科室员工 |
|
||||
| staff | status | idx_staff_status | 按状态查询员工 | 快速筛选特定状态员工 |
|
||||
| indicators | indicator_type | idx_indicator_type | 按指标类型查询 | 快速筛选指标类型 |
|
||||
| assessments | staff_id | idx_assessment_staff | 按员工查询考核记录 | 快速获取员工考核历史 |
|
||||
| assessments | period_year, period_month | idx_assessment_period | 按时间段查询考核记录 | 快速定位特定期间记录 |
|
||||
| assessments | status | idx_assessment_status | 按状态查询考核记录 | 快速筛选特定状态记录 |
|
||||
| assessment_details | assessment_id | idx_detail_assessment | 按考核记录查询明细 | 快速获取考核明细 |
|
||||
| assessment_details | indicator_id | idx_detail_indicator | 按指标查询明细 | 快速获取指标相关明细 |
|
||||
| salary_records | staff_id | idx_salary_staff | 按员工查询工资记录 | 快速获取员工工资历史 |
|
||||
| salary_records | period_year, period_month | idx_salary_period | 按时间段查询工资记录 | 快速定位特定期间工资 |
|
||||
| users | username | idx_user_username | 按用户名查询用户 | 快速定位用户账户 |
|
||||
| performance_plans | plan_level | idx_plan_level | 按计划层级查询 | 快速筛选特定层级计划 |
|
||||
| performance_plans | plan_year | idx_plan_year | 按年度查询计划 | 快速定位年度计划 |
|
||||
| performance_plans | department_id | idx_plan_department | 按科室查询计划 | 快速获取科室计划 |
|
||||
| performance_plans | status | idx_plan_status | 按状态查询计划 | 快速筛选特定状态计划 |
|
||||
| indicator_templates | template_type | idx_template_type | 按模板类型查询 | 快速筛选模板类型 |
|
||||
| indicator_templates | is_active | idx_template_active | 按启用状态查询 | 快速筛选有效模板 |
|
||||
| plan_kpi_relations | plan_id | idx_relation_plan | 按计划查询关联 | 快速获取计划关联指标 |
|
||||
| plan_kpi_relations | indicator_id | idx_relation_indicator | 按指标查询关联 | 快速获取指标关联计划 |
|
||||
| template_indicators | template_id | idx_ti_template | 按模板查询关联 | 快速获取模板关联指标 |
|
||||
| template_indicators | indicator_id | idx_ti_indicator | 按指标查询关联 | 快速获取指标关联模板 |
|
||||
| department_finances | department_id | idx_finance_dept | 按科室查询财务记录 | 快速获取科室财务数据 |
|
||||
| department_finances | period_year, period_month | idx_finance_period | 按时间段查询财务记录 | 快速定位特定期间财务 |
|
||||
| department_finances | finance_type | idx_finance_type | 按财务类型查询 | 快速筛选收支类型 |
|
||||
| department_finances | category | idx_finance_category | 按类别查询财务记录 | 快速筛选特定类别 |
|
||||
|
||||
#### 复合索引设计思路
|
||||
|
||||
复合索引通过组合多个字段来优化特定查询模式:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
QueryPattern[查询模式分析] --> IdentifyFields["识别查询字段"]
|
||||
IdentifyFields --> Selectivity["评估选择性"]
|
||||
Selectivity --> OrderFields["确定字段顺序"]
|
||||
OrderFields --> TestPerformance["测试查询性能"]
|
||||
TestPerformance --> CreateIndex["创建复合索引"]
|
||||
CreateIndex --> MonitorUsage["监控索引使用"]
|
||||
MonitorUsage --> OptimizeIndex["优化索引设计"]
|
||||
subgraph "复合索引示例"
|
||||
PeriodIndex["idx_assessment_period<br/>(year, month)"]
|
||||
RelationIndex["idx_ti_unique<br/>(template_id, indicator_id)"]
|
||||
PlanIndex["idx_plan_department<br/>(department_id, status)"]
|
||||
end
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L176-L176)
|
||||
- [models.py](file://backend/app/models/models.py#L436-L436)
|
||||
- [models.py](file://backend/app/models/models.py#L309-L309)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L82-L85)
|
||||
- [models.py](file://backend/app/models/models.py#L111-L114)
|
||||
- [models.py](file://backend/app/models/models.py#L174-L178)
|
||||
- [models.py](file://backend/app/models/models.py#L227-L230)
|
||||
- [models.py](file://backend/app/models/models.py#L258-L260)
|
||||
- [models.py](file://backend/app/models/models.py#L306-L311)
|
||||
- [models.py](file://backend/app/models/models.py#L433-L437)
|
||||
|
||||
### 约束冲突处理策略
|
||||
|
||||
当数据库约束被违反时,系统需要有一套完善的冲突处理机制。
|
||||
|
||||
#### 错误处理流程
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant App as 应用程序
|
||||
participant DB as 数据库
|
||||
participant Handler as 错误处理器
|
||||
App->>DB : 执行数据库操作
|
||||
DB->>DB : 验证所有约束
|
||||
alt 约束验证失败
|
||||
DB->>Handler : 抛出约束异常
|
||||
Handler->>Handler : 分析异常类型
|
||||
Handler->>Handler : 生成用户友好错误消息
|
||||
Handler->>App : 返回错误响应
|
||||
else 约束验证成功
|
||||
DB->>App : 返回成功响应
|
||||
end
|
||||
```
|
||||
|
||||
#### 约束冲突类型及处理
|
||||
|
||||
| 冲突类型 | 触发条件 | 处理策略 | 用户反馈 |
|
||||
|---------|---------|---------|---------|
|
||||
| 唯一性冲突 | 插入重复唯一值 | 提示用户修改唯一字段值 | "该[字段]已存在,请使用其他值" |
|
||||
| 外键冲突 | 引用不存在的外键值 | 提示用户选择有效引用值 | "请选择有效的[关联实体]" |
|
||||
| 检查约束冲突 | 数据不符合检查条件 | 提示用户修正数据格式 | "[字段]必须满足[条件说明]" |
|
||||
| 级联删除冲突 | 尝试删除有子记录的父记录 | 提示用户先删除子记录或调整级联策略 | "请先删除子记录或调整关联关系" |
|
||||
|
||||
**章节来源**
|
||||
- [main.py](file://backend/app/main.py#L58-L74)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
系统约束设计涉及多个层面的依赖关系,形成了完整的数据完整性保障体系。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "模型层依赖"
|
||||
ModelBase[Base Model]
|
||||
ConstraintMixin[Constraint Mixin]
|
||||
IndexMixin[Index Mixin]
|
||||
end
|
||||
subgraph "约束实现"
|
||||
UniqueConstraint[Unique Constraint]
|
||||
CheckConstraint[Check Constraint]
|
||||
ForeignKeyConstraint[Foreign Key Constraint]
|
||||
IndexConstraint[Index Constraint]
|
||||
end
|
||||
subgraph "迁移层依赖"
|
||||
AlembicOps[Alembic Operations]
|
||||
MigrationScripts[Migration Scripts]
|
||||
end
|
||||
subgraph "配置层依赖"
|
||||
DatabaseConfig[Database Configuration]
|
||||
AsyncEngine[Async Engine]
|
||||
SessionManager[Session Manager]
|
||||
end
|
||||
ModelBase --> ConstraintMixin
|
||||
ModelBase --> IndexMixin
|
||||
ConstraintMixin --> UniqueConstraint
|
||||
ConstraintMixin --> CheckConstraint
|
||||
IndexMixin --> IndexConstraint
|
||||
AlembicOps --> MigrationScripts
|
||||
DatabaseConfig --> AsyncEngine
|
||||
AsyncEngine --> SessionManager
|
||||
MigrationScripts --> UniqueConstraint
|
||||
MigrationScripts --> CheckConstraint
|
||||
MigrationScripts --> ForeignKeyConstraint
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L23-L25)
|
||||
- [database.py](file://backend/app/core/database.py#L10-L20)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L21-L21)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
- [config.py](file://backend/app/core/config.py#L18-L21)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
合理的约束设计不仅保证数据完整性,还能显著提升系统性能。
|
||||
|
||||
### 索引性能优化
|
||||
|
||||
#### 查询性能分析
|
||||
|
||||
| 查询类型 | 索引使用情况 | 性能影响 | 优化建议 |
|
||||
|---------|---------|---------|---------|
|
||||
| 等值查询 | 使用精确匹配索引 | 高性能 | 确保查询条件包含索引字段 |
|
||||
| 范围查询 | 使用范围扫描索引 | 中等性能 | 优化查询条件,减少扫描范围 |
|
||||
| 复合查询 | 使用复合索引 | 高性能 | 确保查询条件覆盖索引前缀 |
|
||||
| 排序查询 | 使用排序索引 | 高性能 | 确保ORDER BY字段包含在索引中 |
|
||||
| 连接查询 | 使用连接索引 | 高性能 | 确保JOIN字段建立索引 |
|
||||
|
||||
#### 索引维护策略
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Monitor[监控索引使用] --> AnalyzeUsage["分析索引使用率"]
|
||||
AnalyzeUsage --> IdentifyUnused["识别未使用索引"]
|
||||
IdentifyUnused --> DropUnused["删除无用索引"]
|
||||
AnalyzeUsage --> IdentifyMissing["识别缺失索引"]
|
||||
IdentifyMissing --> CreateIndex["创建必要索引"]
|
||||
CreateIndex --> Monitor
|
||||
DropUnused --> Monitor
|
||||
Monitor --> RebuildIndex["重建碎片索引"]
|
||||
RebuildIndex --> Monitor
|
||||
```
|
||||
|
||||
### 约束对性能的影响
|
||||
|
||||
| 约束类型 | 正面影响 | 负面影响 | 性能平衡点 |
|
||||
|---------|---------|---------|---------|
|
||||
| 唯一性约束 | 数据一致性保证 | 插入/更新时额外检查 | 在高频写入场景下适度放宽 |
|
||||
| 检查约束 | 业务规则强制执行 | 数据验证开销 | 复杂检查约束需要谨慎使用 |
|
||||
| 外键约束 | 参照完整性保障 | 关联查询性能影响 | 对频繁关联查询考虑性能权衡 |
|
||||
| 索引约束 | 查询性能提升 | 写入性能下降 | 基于查询模式优化索引设计 |
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见约束问题诊断
|
||||
|
||||
#### 唯一性约束冲突
|
||||
|
||||
**问题症状**:插入或更新数据时报唯一性约束错误
|
||||
|
||||
**诊断步骤**:
|
||||
1. 检查冲突的具体字段和值
|
||||
2. 验证是否存在重复数据
|
||||
3. 确认业务逻辑是否允许重复
|
||||
4. 检查数据清理流程
|
||||
|
||||
**解决方案**:
|
||||
- 修改唯一字段值
|
||||
- 清理重复数据
|
||||
- 调整业务逻辑
|
||||
- 重新设计唯一性策略
|
||||
|
||||
#### 外键约束冲突
|
||||
|
||||
**问题症状**:引用不存在的数据时报外键约束错误
|
||||
|
||||
**诊断步骤**:
|
||||
1. 确认被引用表中是否存在对应记录
|
||||
2. 检查关联字段的数据类型和格式
|
||||
3. 验证数据插入顺序
|
||||
4. 检查是否有级联删除策略
|
||||
|
||||
**解决方案**:
|
||||
- 先插入父记录再插入子记录
|
||||
- 使用正确的关联值
|
||||
- 调整级联删除策略
|
||||
- 实施数据预校验
|
||||
|
||||
#### 检查约束冲突
|
||||
|
||||
**问题症状**:数据不符合检查条件时报错
|
||||
|
||||
**诊断步骤**:
|
||||
1. 检查具体违反的约束条件
|
||||
2. 验证数据格式和范围
|
||||
3. 确认业务规则合理性
|
||||
4. 检查数据转换逻辑
|
||||
|
||||
**解决方案**:
|
||||
- 修正数据格式
|
||||
- 调整业务规则
|
||||
- 实施数据验证
|
||||
- 优化约束条件
|
||||
|
||||
### 数据库迁移问题
|
||||
|
||||
#### 迁移失败处理
|
||||
|
||||
**常见问题**:
|
||||
- 字段已存在导致迁移失败
|
||||
- 索引创建冲突
|
||||
- 外键约束依赖问题
|
||||
|
||||
**处理策略**:
|
||||
1. 检查当前数据库状态
|
||||
2. 手动执行必要的DDL操作
|
||||
3. 调整迁移脚本顺序
|
||||
4. 实施回滚和重试机制
|
||||
|
||||
**章节来源**
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L67-L90)
|
||||
|
||||
## 结论
|
||||
|
||||
本系统的数据库约束设计体现了多层次、全方位的数据完整性保障机制。通过合理运用唯一性约束、检查约束、外键约束和索引约束,系统在保证数据准确性和一致性的前提下,实现了高效的查询性能和良好的扩展性。
|
||||
|
||||
### 设计亮点
|
||||
|
||||
1. **层次化约束设计**:从模型层到数据库层的完整约束覆盖
|
||||
2. **业务导向的约束策略**:每个约束都有明确的业务意义和触发条件
|
||||
3. **性能优化的索引设计**:针对高频查询场景的复合索引策略
|
||||
4. **完善的冲突处理机制**:从技术层面到用户体验的全面考虑
|
||||
|
||||
### 持续改进建议
|
||||
|
||||
1. **监控和分析**:建立约束使用情况的监控机制
|
||||
2. **定期优化**:根据查询模式变化调整索引策略
|
||||
3. **文档完善**:持续更新约束设计文档和最佳实践
|
||||
4. **性能测试**:定期进行约束对性能影响的评估测试
|
||||
|
||||
通过这套完整的约束设计体系,系统能够可靠地支撑医院绩效管理的各项业务需求,为医疗质量管理提供坚实的数据基础。
|
||||
471
.qoder/repowiki/zh/content/数据模型详解/数据模型详解.md
Normal file
471
.qoder/repowiki/zh/content/数据模型详解/数据模型详解.md
Normal file
@@ -0,0 +1,471 @@
|
||||
# 数据模型详解
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [finance.py](file://backend/app/models/finance.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [database.py](file://backend/app/core/database.py)
|
||||
- [config.py](file://backend/app/core/config.py)
|
||||
- [init_db.py](file://backend/init_db.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
本文件面向医院绩效系统的核心数据模型,系统化阐述 Department、Staff、Assessment、AssessmentDetail、SalaryRecord 等关键实体的设计理念、字段定义、数据类型与约束条件,并深入解析模型间的关系映射、级联操作与数据完整性保障机制。同时,结合服务层业务逻辑,给出数据验证规则、业务规则实现、性能优化策略、模型扩展指南以及版本兼容与迁移策略,帮助开发者与运维人员高效理解与维护该数据模型。
|
||||
|
||||
## 项目结构
|
||||
后端采用 SQLAlchemy ORM + Alembic 迁移的架构,模型集中于 models 模块,配合 Pydantic 的数据模式(schemas)进行输入输出校验;数据库连接通过异步引擎与会话工厂实现;迁移脚本确保数据库结构演进的可控性。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "模型层"
|
||||
M1["models.py<br/>核心业务模型"]
|
||||
M2["finance.py<br/>财务核算模型"]
|
||||
end
|
||||
subgraph "数据模式层"
|
||||
S1["schemas.py<br/>Pydantic模式"]
|
||||
end
|
||||
subgraph "基础设施层"
|
||||
C1["config.py<br/>配置"]
|
||||
D1["database.py<br/>数据库连接"]
|
||||
end
|
||||
subgraph "迁移层"
|
||||
V1["001_initial.py<br/>初始版本"]
|
||||
V2["002_template.py<br/>模板版本"]
|
||||
end
|
||||
subgraph "服务层"
|
||||
A1["assessment_service.py"]
|
||||
S2["salary_service.py"]
|
||||
ST1["staff_service.py"]
|
||||
I1["indicator_service.py"]
|
||||
end
|
||||
M1 --> S1
|
||||
M2 --> S1
|
||||
C1 --> D1
|
||||
V1 --> M1
|
||||
V2 --> M1
|
||||
A1 --> M1
|
||||
S2 --> M1
|
||||
ST1 --> M1
|
||||
I1 --> M1
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L230)
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
- [database.py](file://backend/app/core/database.py#L9-L39)
|
||||
- [config.py](file://backend/app/core/config.py#L9-L47)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L21-L183)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L21-L96)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [finance.py](file://backend/app/models/finance.py#L1-L79)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
- [config.py](file://backend/app/core/config.py#L1-L47)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L1-L183)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L1-L96)
|
||||
|
||||
## 核心组件
|
||||
本节聚焦五个关键模型的字段定义、数据类型、约束条件与业务含义。
|
||||
|
||||
- Department(科室信息)
|
||||
- 字段与类型:自增主键、字符串名称与编码(唯一)、枚举类型、层级、排序、启用状态、描述、时间戳
|
||||
- 约束:编码唯一;索引覆盖类型与父级
|
||||
- 关系:自关联父子关系;一对多到 Staff
|
||||
- 业务意义:支撑组织架构与层级管理
|
||||
|
||||
- Staff(员工信息)
|
||||
- 字段与类型:唯一工号、姓名、所属科室外键、职位、职称、联系方式、基本工资、绩效系数、状态、入职日期、时间戳
|
||||
- 约束:工号唯一;索引覆盖科室与状态
|
||||
- 关系:多对一到 Department;一对多到 Assessment、SalaryRecord
|
||||
- 业务意义:员工档案与薪酬基础数据
|
||||
|
||||
- Assessment(考核记录)
|
||||
- 字段与类型:员工外键、考核年月、周期类型、总分、加权得分、状态、考核人/审核人外键、时间戳、备注
|
||||
- 约束:复合索引覆盖员工、年月、状态;级联删除明细
|
||||
- 关系:多对一到 Staff;一对多到 AssessmentDetail
|
||||
- 业务意义:记录单次考核的聚合结果与流转状态
|
||||
|
||||
- AssessmentDetail(考核明细)
|
||||
- 字段与类型:考核记录外键、指标外键、实际值、得分、佐证材料、备注、时间戳
|
||||
- 约束:明细索引覆盖考核与指标
|
||||
- 关系:多对一到 Assessment、Indicator
|
||||
- 业务意义:承载具体指标的得分与证据
|
||||
|
||||
- SalaryRecord(工资核算记录)
|
||||
- 字段与类型:员工外键、年月、基本工资、绩效得分、绩效奖金、扣款、补贴、应发工资、状态、备注、时间戳
|
||||
- 约束:索引覆盖员工与年月
|
||||
- 关系:多对一到 Staff
|
||||
- 业务意义:工资发放依据与统计入口
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L230)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L64-L311)
|
||||
|
||||
## 架构概览
|
||||
数据模型围绕“员工-科室-考核-工资”主线展开,通过外键与关系映射实现强一致的数据完整性;服务层负责业务规则与流程控制,如考核状态机、工资计算与生成、模板导入等。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+enum dept_type
|
||||
+int level
|
||||
+int sort_order
|
||||
+bool is_active
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+children : Department[]
|
||||
+staff : Staff[]
|
||||
}
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+string title
|
||||
+string phone
|
||||
+string email
|
||||
+float base_salary
|
||||
+float performance_ratio
|
||||
+enum status
|
||||
+datetime hire_date
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+department : Department
|
||||
+assessments : Assessment[]
|
||||
+salary_records : SalaryRecord[]
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+string period_type
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+enum status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+staff : Staff
|
||||
+assessor : Staff
|
||||
+reviewer : Staff
|
||||
+details : AssessmentDetail[]
|
||||
}
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+string evidence
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+assessment : Assessment
|
||||
+indicator : Indicator
|
||||
}
|
||||
class SalaryRecord {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float base_salary
|
||||
+float performance_score
|
||||
+float performance_bonus
|
||||
+float deduction
|
||||
+float allowance
|
||||
+float total_salary
|
||||
+string status
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+staff : Staff
|
||||
}
|
||||
Department "1" <-- "many" Staff : "外键"
|
||||
Staff "1" <-- "many" Assessment : "外键"
|
||||
Staff "1" <-- "many" SalaryRecord : "外键"
|
||||
Assessment "1" <-- "many" AssessmentDetail : "级联删除"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L230)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### Department(科室信息)
|
||||
- 设计要点
|
||||
- 使用自关联实现层级树结构,支持多级科室组织
|
||||
- 通过枚举限定科室类型,便于筛选与模板匹配
|
||||
- 索引提升按类型与父子关系查询效率
|
||||
- 业务规则
|
||||
- 启用/停用控制科室参与统计与流程
|
||||
- 层级与排序用于前端树形展示与权限控制
|
||||
- 外键与关系
|
||||
- Department.parent → Department.children(自关联)
|
||||
- Department.staff → Staff(一对多)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L86)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L22-L41)
|
||||
|
||||
### Staff(员工信息)
|
||||
- 设计要点
|
||||
- 唯一工号确保跨系统识别一致性
|
||||
- 绩效系数与基本工资构成工资基础
|
||||
- 状态枚举支持在职、休假、离职、退休等生命周期
|
||||
- 业务规则
|
||||
- 仅在职员工参与考核与工资生成
|
||||
- 基本工资与绩效系数影响最终绩效奖金
|
||||
- 外键与关系
|
||||
- Staff.department → Department
|
||||
- Staff.assessments → Assessment
|
||||
- Staff.salary_records → SalaryRecord
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L114)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L107-L149)
|
||||
- [init_db.py](file://backend/init_db.py#L42-L53)
|
||||
|
||||
### Assessment(考核记录)
|
||||
- 设计要点
|
||||
- 年、月、周期类型组合唯一性避免重复
|
||||
- 总分与加权得分分离,加权由明细权重累积
|
||||
- 状态机驱动流程:草稿→提交→审核→确认/驳回
|
||||
- 业务规则
|
||||
- 仅草稿或驳回状态允许修改
|
||||
- 提交后进入审核流程,审核通过方可确认
|
||||
- 外键与关系
|
||||
- Assessment.staff → Staff
|
||||
- Assessment.assessor/reviewer → Staff
|
||||
- Assessment.details → AssessmentDetail(级联删除)
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 草稿
|
||||
草稿 --> 已提交 : "提交"
|
||||
已提交 --> 已审核 : "审核通过"
|
||||
已提交 --> 已驳回 : "审核驳回"
|
||||
已审核 --> 已确认 : "确认"
|
||||
已确认 --> [*]
|
||||
已驳回 --> 草稿 : "修改后重新提交"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L159-L205)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L79-L262)
|
||||
|
||||
### AssessmentDetail(考核明细)
|
||||
- 设计要点
|
||||
- 明细与指标绑定,支持不同指标的权重与计算
|
||||
- 实际值与得分可独立记录,便于审计与复核
|
||||
- 业务规则
|
||||
- 加权得分来源于指标权重与得分乘积之和
|
||||
- 外键与关系
|
||||
- AssessmentDetail.assessment → Assessment
|
||||
- AssessmentDetail.indicator → Indicator
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L181-L202)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L79-L108)
|
||||
|
||||
### SalaryRecord(工资核算记录)
|
||||
- 设计要点
|
||||
- 应发工资 = 基本工资 + 绩效奖金 + 补贴 - 扣款
|
||||
- 绩效奖金 = 绩效基数 × (绩效得分/100) × 绩效系数
|
||||
- 年月唯一,避免重复发薪
|
||||
- 业务规则
|
||||
- 仅当考核处于“已确认”状态才可生成工资记录
|
||||
- 工资记录状态默认“待处理”,支持后续调整
|
||||
- 外键与关系
|
||||
- SalaryRecord.staff → Staff
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start(["开始"]) --> GetAssessment["获取已确认考核记录"]
|
||||
GetAssessment --> Exists{"是否存在?"}
|
||||
Exists --> |否| End(["结束"])
|
||||
Exists --> |是| CalcBonus["计算绩效奖金"]
|
||||
CalcBonus --> SumTotal["计算应发工资"]
|
||||
SumTotal --> CreateRecord["创建工资记录"]
|
||||
CreateRecord --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L205-L230)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L205-L230)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L70-L199)
|
||||
|
||||
### 财务核算模型(DepartmentFinance)
|
||||
- 设计要点
|
||||
- 收入/支出两类,按类别细分(检查费、检验费、床位费、材料费、人员支出等)
|
||||
- 金额非负约束,确保财务数据正确性
|
||||
- 按科室与年月索引,支持财务统计
|
||||
- 业务规则
|
||||
- 金额必须≥0
|
||||
- 与科室关联,支持按科室维度的收支结余分析
|
||||
|
||||
**章节来源**
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
|
||||
## 依赖分析
|
||||
- 模型依赖
|
||||
- Assessment 依赖 Staff、AssessmentDetail
|
||||
- AssessmentDetail 依赖 Assessment、Indicator
|
||||
- SalaryRecord 依赖 Staff
|
||||
- Department 依赖 Staff(自关联)
|
||||
- 服务层依赖
|
||||
- AssessmentService 依赖 Assessment、AssessmentDetail、Indicator
|
||||
- SalaryService 依赖 Staff、Assessment、SalaryRecord
|
||||
- 其他服务(StaffService、IndicatorService)分别依赖对应模型
|
||||
- 数据库与配置
|
||||
- 异步引擎与会话工厂统一管理连接与事务
|
||||
- Alembic 迁移脚本确保表结构演进
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
A["AssessmentService"] --> AM["Assessment"]
|
||||
A --> ADM["AssessmentDetail"]
|
||||
A --> IM["Indicator"]
|
||||
S["SalaryService"] --> SM["Staff"]
|
||||
S --> AS["Assessment"]
|
||||
S --> SRM["SalaryRecord"]
|
||||
ST["StaffService"] --> STM["Staff"]
|
||||
I["IndicatorService"] --> IM
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L79-L262)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L77-L199)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L16-L112)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py#L16-L197)
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L262)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L1-L199)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py#L1-L197)
|
||||
|
||||
## 性能考虑
|
||||
- 索引策略
|
||||
- 员工:按部门与状态建立索引,加速筛选与分页
|
||||
- 考核:按员工、年月、状态建立复合索引,支持快速定位与统计
|
||||
- 工资:按员工与年月建立索引,提升查询效率
|
||||
- 科室:按类型与父级建立索引,优化树形查询
|
||||
- 查询优化
|
||||
- 使用 selectinload 预加载关联对象,减少 N+1 查询
|
||||
- 分页查询配合 COUNT 子查询,避免全表扫描
|
||||
- 异步与连接池
|
||||
- 异步引擎与连接池配置,提升并发吞吐
|
||||
- 数据类型
|
||||
- 使用 Numeric 精确存储金额与分数,避免浮点误差
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L82-L85)
|
||||
- [models.py](file://backend/app/models/models.py#L111-L114)
|
||||
- [models.py](file://backend/app/models/models.py#L174-L178)
|
||||
- [models.py](file://backend/app/models/models.py#L227-L230)
|
||||
- [config.py](file://backend/app/core/config.py#L18-L22)
|
||||
- [database.py](file://backend/app/core/database.py#L9-L20)
|
||||
|
||||
## 故障排除指南
|
||||
- 常见问题
|
||||
- 无法更新考核:仅草稿或驳回状态允许修改
|
||||
- 无法生成工资:需先完成“已确认”的考核记录
|
||||
- 重复工资:同一年月同员工只允许一条工资记录
|
||||
- 财务异常:金额必须≥0,否则触发约束错误
|
||||
- 排查步骤
|
||||
- 检查 Assessment 状态与时间戳
|
||||
- 核对 Staff 的基本工资与绩效系数
|
||||
- 确认 SalaryRecord 的年月与员工唯一性
|
||||
- 校验 DepartmentFinance 的金额与类别
|
||||
- 日志与调试
|
||||
- 开启数据库回滚与关闭,确保异常时数据一致性
|
||||
- 使用分页与索引优化查询,避免超时
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L111-L156)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
- [finance.py](file://backend/app/models/finance.py#L73-L74)
|
||||
- [database.py](file://backend/app/core/database.py#L28-L39)
|
||||
|
||||
## 结论
|
||||
本数据模型以清晰的实体边界、严谨的外键关系与完善的索引策略为基础,结合服务层的状态机与计算逻辑,实现了从“员工-科室-考核-工资”的闭环管理。通过 Alembic 迁移与 Pydantic 模式,系统具备良好的可演进性与可维护性。建议在扩展新功能时遵循现有命名规范、索引策略与事务处理模式,确保数据一致性与性能表现。
|
||||
|
||||
## 附录
|
||||
|
||||
### 字段定义与约束对照表
|
||||
- Department
|
||||
- 字段:id、name、code(唯一)、dept_type、parent_id、level、sort_order、is_active、description、created_at、updated_at
|
||||
- 约束:唯一索引(code),普通索引(dept_type、parent_id)
|
||||
- Staff
|
||||
- 字段:id、employee_id(唯一)、name、department_id、position、title、phone、email、base_salary、performance_ratio、status、hire_date、created_at、updated_at
|
||||
- 约束:唯一索引(employee_id),普通索引(department_id、status)
|
||||
- Assessment
|
||||
- 字段:id、staff_id、period_year、period_month、period_type、total_score、weighted_score、status、assessor_id、reviewer_id、submit_time、review_time、remark、created_at、updated_at
|
||||
- 约束:普通索引(staff_id、period_year、period_month、status),级联删除明细
|
||||
- AssessmentDetail
|
||||
- 字段:id、assessment_id、indicator_id、actual_value、score、evidence、remark、created_at、updated_at
|
||||
- 约束:普通索引(assessment_id、indicator_id)
|
||||
- SalaryRecord
|
||||
- 字段:id、staff_id、period_year、period_month、base_salary、performance_score、performance_bonus、deduction、allowance、total_salary、status、remark、created_at、updated_at
|
||||
- 约束:普通索引(staff_id、period_year、period_month)
|
||||
- DepartmentFinance
|
||||
- 字段:id、department_id、period_year、period_month、finance_type、category、amount(≥0)、source、remark、created_at、updated_at
|
||||
- 约束:普通索引(department_id、period_year、period_month、finance_type、category),check(amount ≥ 0)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L230)
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
|
||||
### 版本兼容与迁移策略
|
||||
- 初始版本(001_initial.py)
|
||||
- 创建 departments、staff、indicators、assessments、assessment_details、salary_records、users 表
|
||||
- 建立基础索引与外键约束
|
||||
- 模板版本(002_template.py)
|
||||
- 新增 indicator_templates、template_indicators 表
|
||||
- 为 indicators 表动态添加 BSC 维度、目标单位、考核方法、扣分标准、数据来源、适用科室类型、是否 veto 等列
|
||||
- 迁移建议
|
||||
- 新增字段采用条件判断(如字段存在性检查),避免重复执行报错
|
||||
- 对历史数据进行补全(如适用科室类型 JSON 数组),确保业务可用
|
||||
- 升级前备份数据库,升级后验证索引与约束生效
|
||||
|
||||
**章节来源**
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L21-L183)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L21-L96)
|
||||
462
.qoder/repowiki/zh/content/数据模型详解/枚举类型定义.md
Normal file
462
.qoder/repowiki/zh/content/数据模型详解/枚举类型定义.md
Normal file
@@ -0,0 +1,462 @@
|
||||
# 枚举类型定义
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [init_indicator_templates.py](file://backend/init_indicator_templates.py)
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py)
|
||||
- [stats.py](file://backend/app/api/v1/stats.py)
|
||||
- [IMPLEMENTATION_SUMMARY.md](file://IMPLEMENTATION_SUMMARY.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心枚举类型](#核心枚举类型)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
本文档详细介绍了医院绩效管理系统中的所有自定义枚举类型。这些枚举类型是系统的核心数据结构,用于定义和约束业务实体的状态和分类。系统包含五个主要的枚举类型:科室类型(DeptType)、平衡计分卡维度(BSCDimension)、员工状态(StaffStatus)、考核状态(AssessmentStatus)和指标类型(IndicatorType)。
|
||||
|
||||
这些枚举类型不仅在数据库模型中使用,还在API接口、服务层逻辑、统计分析和前端展示等多个层面发挥重要作用,确保了整个系统的数据一致性和业务规则的正确执行。
|
||||
|
||||
## 项目结构
|
||||
|
||||
系统采用典型的三层架构设计,枚举类型分布在不同的层次中:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "数据访问层"
|
||||
Models[models.py<br/>数据库模型]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
Services[services/<br/>服务层]
|
||||
StatsService[stats_service.py<br/>统计服务]
|
||||
AssessmentService[assessment_service.py<br/>考核服务]
|
||||
end
|
||||
subgraph "表示层"
|
||||
API[api/v1/<br/>API接口]
|
||||
IndicatorsAPI[indicators.py<br/>指标API]
|
||||
StatsAPI[stats.py<br/>统计API]
|
||||
Schemas[schemas.py<br/>数据模式]
|
||||
end
|
||||
subgraph "初始化数据"
|
||||
InitTemplates[init_indicator_templates.py<br/>指标模板]
|
||||
end
|
||||
Models --> Services
|
||||
Services --> API
|
||||
Schemas --> API
|
||||
InitTemplates --> Models
|
||||
StatsService --> Models
|
||||
AssessmentService --> Models
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L15-L61)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L44)
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py#L16-L218)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L160-L263)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
## 核心枚举类型
|
||||
|
||||
### 科室类型(DeptType)
|
||||
|
||||
科室类型枚举定义了医院中各种类型的科室分类,从最初的5种扩展到了9种现代医院组织结构。
|
||||
|
||||
| 枚举值 | 值 | 描述 | 适用场景 |
|
||||
|--------|-----|------|----------|
|
||||
| CLINICAL_SURGICAL | clinical_surgical | 手术临床科室 | 外科、骨科、心胸外科等需要手术治疗的科室 |
|
||||
| CLINICAL_NONSURGICAL_WARD | clinical_nonsurgical_ward | 非手术有病房科室 | 内科、儿科、神经内科等有病床的临床科室 |
|
||||
| CLINICAL_NONSURGICAL_NOWARD | clinical_nonsurgical_noward | 非手术无病房科室 | 急诊科、门诊部等无病床的临床科室 |
|
||||
| MEDICAL_TECH | medical_tech | 医技科室 | 检验科、放射科、超声科等医学技术科室 |
|
||||
| MEDICAL_AUXILIARY | medical_auxiliary | 医辅科室 | 病理科、输血科等辅助医疗科室 |
|
||||
| NURSING | nursing | 护理单元 | 各病区护理单元 |
|
||||
| ADMIN | admin | 行政科室 | 人事科、财务科、办公室等行政部门 |
|
||||
| FINANCE | finance | 财务科室 | 财务科、审计科等财务管理部门 |
|
||||
| LOGISTICS | logistics | 后勤保障科室 | 设备科、总务科、保卫科等后勤部门 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L16-L27)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L22)
|
||||
|
||||
### 平衡计分卡维度(BSCDimension)
|
||||
|
||||
平衡计分卡维度枚举提供了四个关键的绩效评估维度,支持全面的组织绩效管理。
|
||||
|
||||
| 枚举值 | 值 | 描述 | 业务意义 |
|
||||
|--------|-----|------|----------|
|
||||
| FINANCIAL | financial | 财务维度 | 关注财务表现和经济效益,如收入增长、成本控制 |
|
||||
| CUSTOMER | customer | 客户维度 | 关注患者满意度和服务质量,如服务态度、治疗效果 |
|
||||
| INTERNAL_PROCESS | internal_process | 内部流程维度 | 关注运营效率和质量控制,如流程标准化、安全指标 |
|
||||
| LEARNING_GROWTH | learning_growth | 学习与成长维度 | 关注员工发展和组织能力提升,如培训参与、技术创新 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L29-L35)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L98-L104)
|
||||
|
||||
### 员工状态(StaffStatus)
|
||||
|
||||
员工状态枚举定义了员工在组织中的不同状态,支持完整的人力资源管理。
|
||||
|
||||
| 枚举值 | 值 | 描述 | 业务规则 |
|
||||
|--------|-----|------|----------|
|
||||
| ACTIVE | active | 在职 | 可参与考核、享受绩效奖金 |
|
||||
| LEAVE | leave | 休假 | 暂停考核,保留绩效记录 |
|
||||
| RESIGNED | resigned | 离职 | 不再参与考核,绩效记录归档 |
|
||||
| RETIRED | retired | 退休 | 不再参与考核,仅保留历史记录 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L37-L43)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L24-L29)
|
||||
|
||||
### 考核状态(AssessmentStatus)
|
||||
|
||||
考核状态枚举实现了完整的考核流程管理,支持多级审核和状态追踪。
|
||||
|
||||
| 枚举值 | 值 | 描述 | 流程作用 |
|
||||
|--------|-----|------|----------|
|
||||
| DRAFT | draft | 草稿 | 初始状态,允许修改和补充 |
|
||||
| SUBMITTED | submitted | 已提交 | 完成填写,等待审核 |
|
||||
| REVIEWED | reviewed | 已审核 | 审核通过,等待最终确认 |
|
||||
| FINALIZED | finalized | 已确认 | 最终状态,生成正式结果 |
|
||||
| REJECTED | rejected | 已驳回 | 审核不通过,需要重新提交 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L45-L52)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L31-L37)
|
||||
|
||||
### 指标类型(IndicatorType)
|
||||
|
||||
指标类型枚举从5种扩展到8种,支持更全面的绩效管理需求。
|
||||
|
||||
| 枚举值 | 值 | 描述 | 适用场景 |
|
||||
|--------|-----|------|----------|
|
||||
| QUALITY | quality | 质量指标 | 关注工作质量和标准达成度 |
|
||||
| QUANTITY | quantity | 数量指标 | 关注工作量和产出数量 |
|
||||
| EFFICIENCY | efficiency | 效率指标 | 关注工作效率和资源利用 |
|
||||
| SERVICE | service | 服务指标 | 关注服务质量和服务水平 |
|
||||
| COST | cost | 成本指标 | 关注成本控制和费用管理 |
|
||||
| SAFETY | safety | 安全指标 | 关注医疗安全和风险管理 |
|
||||
| LEARNING | learning | 学习成长指标 | 关注员工培训和发展 |
|
||||
| COMPLIANCE | compliance | 合规指标 | 关注规章制度执行 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L54-L61)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L39-L44)
|
||||
|
||||
## 架构概览
|
||||
|
||||
枚举类型在整个系统中的应用架构如下:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "数据模型层"
|
||||
DeptTypeModel[DeptType<br/>科室类型模型]
|
||||
BSCDimensionModel[BSCDimension<br/>平衡计分卡维度]
|
||||
StaffStatusModel[StaffStatus<br/>员工状态模型]
|
||||
AssessmentStatusModel[AssessmentStatus<br/>考核状态模型]
|
||||
IndicatorTypeModel[IndicatorType<br/>指标类型模型]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
AssessmentService[AssessmentService<br/>考核服务]
|
||||
StatsService[StatsService<br/>统计服务]
|
||||
IndicatorService[IndicatorService<br/>指标服务]
|
||||
end
|
||||
subgraph "API接口层"
|
||||
AssessmentAPI[AssessmentAPI<br/>考核API]
|
||||
StatsAPI[StatsAPI<br/>统计API]
|
||||
IndicatorAPI[IndicatorAPI<br/>指标API]
|
||||
end
|
||||
subgraph "数据传输层"
|
||||
PydanticSchemas[Pydantic Schemas<br/>数据验证]
|
||||
end
|
||||
DeptTypeModel --> AssessmentService
|
||||
BSCDimensionModel --> StatsService
|
||||
StaffStatusModel --> AssessmentService
|
||||
AssessmentStatusModel --> AssessmentService
|
||||
IndicatorTypeModel --> IndicatorService
|
||||
AssessmentService --> AssessmentAPI
|
||||
StatsService --> StatsAPI
|
||||
IndicatorService --> IndicatorAPI
|
||||
AssessmentAPI --> PydanticSchemas
|
||||
StatsAPI --> PydanticSchemas
|
||||
IndicatorAPI --> PydanticSchemas
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L15-L61)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L44)
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py#L16-L218)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L160-L263)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 数据模型中的枚举使用
|
||||
|
||||
在数据模型中,枚举类型被用作SQLAlchemy列类型,确保数据库存储的一致性:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+DeptType dept_type
|
||||
+int parent_id
|
||||
+int level
|
||||
+int sort_order
|
||||
+bool is_active
|
||||
+string description
|
||||
}
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+string title
|
||||
+string phone
|
||||
+string email
|
||||
+float base_salary
|
||||
+float performance_ratio
|
||||
+StaffStatus status
|
||||
+datetime hire_date
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+string period_type
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentStatus status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
}
|
||||
Department --> DeptType : uses
|
||||
Staff --> StaffStatus : uses
|
||||
Assessment --> AssessmentStatus : uses
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L178)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L178)
|
||||
|
||||
### 服务层中的枚举应用
|
||||
|
||||
服务层通过枚举类型实现业务逻辑控制:
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant API as API接口
|
||||
participant Service as 服务层
|
||||
participant Model as 数据模型
|
||||
participant DB as 数据库
|
||||
API->>Service : 提交考核请求
|
||||
Service->>Model : 获取考核记录
|
||||
Model->>DB : 查询数据库
|
||||
DB-->>Model : 返回考核数据
|
||||
Model-->>Service : 返回Assessment对象
|
||||
Service->>Service : 检查AssessmentStatus
|
||||
alt 状态为DRAFT
|
||||
Service->>Service : 设置状态为SUBMITTED
|
||||
Service->>DB : 更新数据库
|
||||
DB-->>Service : 更新成功
|
||||
Service-->>API : 返回更新后的考核
|
||||
else 状态不正确
|
||||
Service-->>API : 返回错误
|
||||
end
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L160-L205)
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L160-L205)
|
||||
|
||||
### 统计分析中的枚举使用
|
||||
|
||||
统计服务利用枚举类型进行数据分析:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始统计]) --> GetParams[获取查询参数]
|
||||
GetParams --> FilterStatus[过滤已确认状态]
|
||||
FilterStatus --> GroupByDim[按BSC维度分组]
|
||||
GroupByDim --> CalcScore[计算维度得分]
|
||||
CalcScore --> CalcWeight[计算权重和指标数量]
|
||||
CalcWeight --> FormatResult[格式化结果]
|
||||
FormatResult --> End([返回统计结果])
|
||||
FilterStatus --> |使用AssessmentStatus.FINALIZED| FilterStatus
|
||||
GroupByDim --> |使用BSCDimension枚举| GroupByDim
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py#L20-L72)
|
||||
|
||||
**章节来源**
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py#L20-L72)
|
||||
|
||||
### API接口中的枚举应用
|
||||
|
||||
API接口层通过Pydantic模式使用枚举类型:
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
subgraph "API请求"
|
||||
Request[HTTP请求]
|
||||
Params[查询参数]
|
||||
end
|
||||
subgraph "Pydantic验证"
|
||||
IndicatorSchema[IndicatorSchema]
|
||||
DeptTypeEnum[DeptType枚举]
|
||||
IndicatorTypeEnum[IndicatorType枚举]
|
||||
end
|
||||
subgraph "业务处理"
|
||||
Service[服务层]
|
||||
DB[数据库操作]
|
||||
end
|
||||
Request --> IndicatorSchema
|
||||
Params --> IndicatorSchema
|
||||
IndicatorSchema --> DeptTypeEnum
|
||||
IndicatorSchema --> IndicatorTypeEnum
|
||||
IndicatorSchema --> Service
|
||||
Service --> DB
|
||||
DB --> Service
|
||||
Service --> IndicatorSchema
|
||||
IndicatorSchema --> Response[HTTP响应]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py#L20-L41)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L153-L192)
|
||||
|
||||
**章节来源**
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py#L20-L41)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L153-L192)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
枚举类型之间的依赖关系和使用模式:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "核心枚举"
|
||||
DeptType[DeptType]
|
||||
BSCDimension[BSCDimension]
|
||||
StaffStatus[StaffStatus]
|
||||
AssessmentStatus[AssessmentStatus]
|
||||
IndicatorType[IndicatorType]
|
||||
end
|
||||
subgraph "数据模型"
|
||||
Department[Department模型]
|
||||
Staff[Staff模型]
|
||||
Assessment[Assessment模型]
|
||||
Indicator[Indicator模型]
|
||||
end
|
||||
subgraph "服务层"
|
||||
AssessmentService[AssessmentService]
|
||||
StatsService[StatsService]
|
||||
IndicatorService[IndicatorService]
|
||||
end
|
||||
subgraph "API层"
|
||||
AssessmentAPI[AssessmentAPI]
|
||||
StatsAPI[StatsAPI]
|
||||
IndicatorAPI[IndicatorAPI]
|
||||
end
|
||||
DeptType --> Department
|
||||
StaffStatus --> Staff
|
||||
AssessmentStatus --> Assessment
|
||||
BSCDimension --> Indicator
|
||||
IndicatorType --> Indicator
|
||||
Department --> AssessmentService
|
||||
Staff --> AssessmentService
|
||||
Assessment --> AssessmentService
|
||||
Indicator --> IndicatorService
|
||||
AssessmentService --> AssessmentAPI
|
||||
StatsService --> StatsAPI
|
||||
IndicatorService --> IndicatorAPI
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L178)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L44)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L178)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L44)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
枚举类型在系统中的性能优势:
|
||||
|
||||
1. **内存效率**:枚举值在内存中只存储一次,避免重复字符串存储
|
||||
2. **类型安全**:编译时检查,减少运行时错误
|
||||
3. **数据库优化**:使用SQLAlchemy Enum类型,数据库层面的约束和索引优化
|
||||
4. **序列化效率**:字符串枚举值在网络传输中占用更少空间
|
||||
|
||||
最佳实践建议:
|
||||
- 在数据库查询中使用枚举值进行WHERE条件过滤
|
||||
- 在API响应中使用字符串形式的枚举值便于前端处理
|
||||
- 在服务层逻辑中使用枚举类型进行状态判断和流程控制
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
常见问题和解决方案:
|
||||
|
||||
### 枚举值不匹配问题
|
||||
**问题**:API请求中的枚举值与数据库存储不一致
|
||||
**解决方案**:
|
||||
- 确保API层使用正确的枚举类型
|
||||
- 在数据验证阶段添加枚举值检查
|
||||
- 使用统一的枚举转换函数
|
||||
|
||||
### 状态流转异常
|
||||
**问题**:考核状态无法正常流转
|
||||
**解决方案**:
|
||||
- 检查AssessmentStatus的流转顺序
|
||||
- 验证当前状态与预期状态的匹配
|
||||
- 添加状态检查和错误处理逻辑
|
||||
|
||||
### 维度统计错误
|
||||
**问题**:BSC维度统计结果不正确
|
||||
**解决方案**:
|
||||
- 验证BSCDimension枚举值的使用
|
||||
- 检查数据库中指标的维度设置
|
||||
- 确认统计查询的JOIN条件和WHERE条件
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L160-L205)
|
||||
- [stats_service.py](file://backend/app/services/stats_service.py#L20-L72)
|
||||
|
||||
## 结论
|
||||
|
||||
枚举类型是医院绩效管理系统的核心基础设施,它们提供了:
|
||||
|
||||
1. **业务一致性**:确保不同模块间使用相同的业务概念和规则
|
||||
2. **类型安全**:在编译时发现潜在的类型错误
|
||||
3. **维护便利**:集中管理业务规则,便于后续扩展和修改
|
||||
4. **性能优化**:减少字符串比较,提高系统运行效率
|
||||
|
||||
通过合理设计和使用这些枚举类型,系统能够支持复杂的医院绩效管理需求,包括多维度的平衡计分卡分析、完整的考核流程管理和全面的统计报表功能。这些枚举类型为系统的稳定性和可维护性奠定了坚实的基础。
|
||||
|
||||
随着系统的持续发展,这些枚举类型将继续发挥重要作用,支持新的业务需求和功能扩展。
|
||||
476
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/员工信息模型.md
Normal file
476
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/员工信息模型.md
Normal file
@@ -0,0 +1,476 @@
|
||||
# 员工信息模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [staff.py](file://backend/app/api/v1/staff.py)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py)
|
||||
- [database.md](file://docs/database.md)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
员工信息模型是医院绩效管理系统的核心数据模型之一,负责管理医院全体员工的基础信息、状态管理和薪资相关信息。该模型采用现代化的ORM设计,结合枚举类型、关系映射和约束机制,确保数据的完整性和一致性。
|
||||
|
||||
本模型不仅存储员工的基本信息,还通过复杂的业务逻辑处理员工状态变化对系统其他模块的影响,包括与科室的多对一关系、与考核记录的一对多关系、以及与工资记录的一对多关系。
|
||||
|
||||
## 项目结构
|
||||
|
||||
基于仓库的实际结构,员工信息模型主要分布在以下文件中:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "后端架构"
|
||||
A[models.py<br/>数据模型定义]
|
||||
B[schemas.py<br/>数据验证模式]
|
||||
C[staff.py<br/>API路由]
|
||||
D[staff_service.py<br/>业务服务层]
|
||||
E[salary_service.py<br/>工资服务层]
|
||||
end
|
||||
subgraph "数据库层"
|
||||
F[database.md<br/>数据库设计文档]
|
||||
G[001_initial.py<br/>数据库迁移脚本]
|
||||
end
|
||||
A --> B
|
||||
A --> C
|
||||
A --> D
|
||||
A --> E
|
||||
C --> D
|
||||
D --> A
|
||||
E --> A
|
||||
F --> A
|
||||
G --> A
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L107-L149)
|
||||
- [staff.py](file://backend/app/api/v1/staff.py#L1-L124)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
## 核心组件
|
||||
|
||||
### 员工状态枚举 (StaffStatus)
|
||||
|
||||
员工状态枚举定义了四种核心状态,每种状态都有明确的业务含义:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class StaffStatus {
|
||||
<<enumeration>>
|
||||
+ACTIVE
|
||||
+LEAVE
|
||||
+RESIGNED
|
||||
+RETIRED
|
||||
}
|
||||
note for StaffStatus : "员工状态枚举\n- ACTIVE : 在职\n- LEAVE : 休假\n- RESIGNED : 离职\n- RETIRED : 退休"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L37-L43)
|
||||
|
||||
### 员工实体模型
|
||||
|
||||
员工实体模型包含了完整的员工信息结构:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+string title
|
||||
+string phone
|
||||
+string email
|
||||
+float base_salary
|
||||
+float performance_ratio
|
||||
+StaffStatus status
|
||||
+datetime hire_date
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+Department department
|
||||
+Assessment[] assessments
|
||||
+SalaryRecord[] salary_records
|
||||
}
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+DeptType dept_type
|
||||
+int parent_id
|
||||
+int level
|
||||
+int sort_order
|
||||
+bool is_active
|
||||
+string description
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+string period_type
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentStatus status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
}
|
||||
class SalaryRecord {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float base_salary
|
||||
+float performance_score
|
||||
+float performance_bonus
|
||||
+float deduction
|
||||
+float allowance
|
||||
+float total_salary
|
||||
+string status
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
}
|
||||
Staff --> Department : "多对一"
|
||||
Staff --> Assessment : "一对多"
|
||||
Staff --> SalaryRecord : "一对多"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [models.py](file://backend/app/models/models.py#L62-L80)
|
||||
- [models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [models.py](file://backend/app/models/models.py#L205-L230)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L115)
|
||||
|
||||
## 架构概览
|
||||
|
||||
员工信息模型在整个系统架构中扮演着核心角色,连接着多个业务模块:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "表现层"
|
||||
A[前端界面]
|
||||
B[API网关]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
C[员工管理API]
|
||||
D[员工服务层]
|
||||
E[工资服务层]
|
||||
F[统计服务层]
|
||||
end
|
||||
subgraph "数据访问层"
|
||||
G[员工模型]
|
||||
H[科室模型]
|
||||
I[考核模型]
|
||||
J[工资模型]
|
||||
end
|
||||
subgraph "数据存储"
|
||||
K[员工表]
|
||||
L[科室表]
|
||||
M[考核表]
|
||||
N[工资记录表]
|
||||
end
|
||||
A --> B
|
||||
B --> C
|
||||
C --> D
|
||||
C --> E
|
||||
C --> F
|
||||
D --> G
|
||||
D --> H
|
||||
E --> G
|
||||
E --> I
|
||||
E --> J
|
||||
G --> K
|
||||
H --> L
|
||||
I --> M
|
||||
J --> N
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [staff.py](file://backend/app/api/v1/staff.py#L1-L124)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L1-L260)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 员工状态管理
|
||||
|
||||
员工状态管理是系统中最复杂的业务逻辑之一,不同状态对系统行为产生不同的影响:
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 在职
|
||||
在职 --> 休假 : "LEAVE"
|
||||
在职 --> 离职 : "RESIGNED"
|
||||
在职 --> 退休 : "RETIRED"
|
||||
休假 --> 在职 : "恢复工作"
|
||||
休假 --> 离职 : "转为离职"
|
||||
休假 --> 退休 : "转为退休"
|
||||
离职 --> [*]
|
||||
退休 --> [*]
|
||||
note right of 在职 : "可参与考核\n可生成工资记录\n可进行系统操作"
|
||||
note right of 休假 : "暂停考核\n暂停工资计算\n但仍可查看信息"
|
||||
note right of 离职 : "完全停止系统访问\n历史数据保留"
|
||||
note right of 退休 : "特殊权限限制\n历史数据可查看"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L37-L43)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L104-L112)
|
||||
|
||||
#### 状态变更对系统的影响
|
||||
|
||||
1. **考核模块影响**:
|
||||
- 休假员工:暂停考核流程,但可查看历史考核记录
|
||||
- 离职/退休员工:无法参与新的考核,仅能查看历史记录
|
||||
|
||||
2. **工资模块影响**:
|
||||
- 休假员工:暂停工资计算,但可查看历史工资记录
|
||||
- 离职/退休员工:不再生成新的工资记录
|
||||
|
||||
3. **权限控制影响**:
|
||||
- 离职/退休员工:系统访问权限被限制
|
||||
- 休假员工:部分功能受限
|
||||
|
||||
**章节来源**
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L104-L112)
|
||||
|
||||
### 工号唯一性设计
|
||||
|
||||
工号作为员工的唯一标识符,在系统中具有极高的重要性:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[员工创建请求] --> B{检查工号是否存在}
|
||||
B --> |是| C[返回错误: 工号已存在]
|
||||
B --> |否| D[验证工号格式]
|
||||
D --> E{格式验证通过?}
|
||||
E --> |否| F[返回错误: 工号格式不正确]
|
||||
E --> |是| G[创建员工记录]
|
||||
G --> H[返回成功响应]
|
||||
I[员工更新请求] --> J{检查工号是否被其他员工使用}
|
||||
J --> |是| K[返回错误: 工号已被使用]
|
||||
J --> |否| L[更新员工记录]
|
||||
L --> M[返回成功响应]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [staff.py](file://backend/app/api/v1/staff.py#L75-L78)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L62-L67)
|
||||
|
||||
### 薪资系数设计
|
||||
|
||||
薪资系数是绩效工资计算的核心参数,直接影响最终的绩效奖金:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[绩效奖金计算] --> B[获取员工绩效系数]
|
||||
B --> C[获取考核加权得分]
|
||||
B --> D[获取绩效基数]
|
||||
C --> E[计算公式]
|
||||
D --> E
|
||||
D --> F[绩效奖金 = 绩效基数 × (加权得分/100) × 绩效系数]
|
||||
E --> F
|
||||
F --> G[生成工资记录]
|
||||
H[默认系数] --> I[1.0]
|
||||
J[最小系数] --> K[0.0]
|
||||
L[最大系数] --> M[5.0]
|
||||
note right of F : "示例: 基础工资8000元\n绩效系数1.2\n加权得分85分\n绩效奖金 = 3000 × (85/100) × 1.2 = 3060元"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L167-L170)
|
||||
|
||||
**章节来源**
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L17-L18)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
|
||||
### 联系方式维护
|
||||
|
||||
员工联系方式的维护遵循严格的验证规则:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class ContactInfo {
|
||||
+string phone
|
||||
+string email
|
||||
+validatePhone(phone) bool
|
||||
+validateEmail(email) bool
|
||||
+formatPhone(phone) string
|
||||
+formatEmail(email) string
|
||||
}
|
||||
note for ContactInfo : "联系方式验证规则\n- 电话 : 最多20位数字\n- 邮箱 : 符合标准邮箱格式\n- 支持空值"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L126-L136)
|
||||
|
||||
### 职位职称管理
|
||||
|
||||
职位和职称信息用于区分员工的专业水平和职责范围:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class PositionManagement {
|
||||
+string position
|
||||
+string title
|
||||
+validatePosition(position) bool
|
||||
+validateTitle(title) bool
|
||||
+getPositionLevel(position) int
|
||||
+getTitleRank(title) int
|
||||
}
|
||||
note for PositionManagement : "职位管理\n- position : 职位名称\n- title : 职称等级\n- 支持空值\n- 用于权限和薪酬分级"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L96-L98)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L112-L117)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
员工信息模型与其他模块的依赖关系如下:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "核心依赖"
|
||||
A[Staff模型] --> B[Department模型]
|
||||
A --> C[Assessment模型]
|
||||
A --> D[SalaryRecord模型]
|
||||
end
|
||||
subgraph "服务层依赖"
|
||||
E[StaffService] --> A
|
||||
E --> B
|
||||
F[SalaryService] --> A
|
||||
F --> C
|
||||
F --> D
|
||||
end
|
||||
subgraph "API层依赖"
|
||||
G[StaffAPI] --> E
|
||||
H[SalaryAPI] --> F
|
||||
end
|
||||
subgraph "数据验证"
|
||||
I[StaffCreate] --> A
|
||||
J[StaffUpdate] --> A
|
||||
K[StaffResponse] --> A
|
||||
end
|
||||
A -.-> L[StaffStatus枚举]
|
||||
B -.-> M[DeptType枚举]
|
||||
C -.-> N[AssessmentStatus枚举]
|
||||
D -.-> O[SalaryStatus枚举]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L9-L10)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L10-L11)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L1-L260)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 查询优化策略
|
||||
|
||||
1. **索引设计**:
|
||||
- 员工表:`idx_staff_dept`(科室ID)、`idx_staff_status`(状态)
|
||||
- 考核表:`idx_assessment_staff`(员工ID)、`idx_assessment_period`(考核周期)
|
||||
- 工资表:`idx_salary_staff`(员工ID)、`idx_salary_period`(考核周期)
|
||||
|
||||
2. **查询优化**:
|
||||
- 使用`selectinload`进行关联查询优化
|
||||
- 实现分页查询避免大数据量加载
|
||||
- 缓存常用查询结果
|
||||
|
||||
### 数据完整性保证
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[数据操作] --> B[输入验证]
|
||||
B --> C[业务规则检查]
|
||||
C --> D[数据库约束验证]
|
||||
D --> E[事务处理]
|
||||
E --> F[数据持久化]
|
||||
G[输入验证] --> H[字段长度验证]
|
||||
G --> I[格式验证]
|
||||
G --> J[范围验证]
|
||||
K[业务规则检查] --> L[工号唯一性]
|
||||
K --> M[状态有效性]
|
||||
K --> N[关联关系验证]
|
||||
O[数据库约束验证] --> P[唯一约束]
|
||||
O --> Q[外键约束]
|
||||
O --> R[检查约束]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L107-L136)
|
||||
- [models.py](file://backend/app/models/models.py#L93-L114)
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题及解决方案
|
||||
|
||||
1. **工号重复错误**
|
||||
- 症状:创建员工时返回"工号已存在"
|
||||
- 解决:检查现有员工列表,使用唯一工号
|
||||
|
||||
2. **状态变更异常**
|
||||
- 症状:员工状态无法正常切换
|
||||
- 解决:检查状态枚举值的有效性,确认业务流程
|
||||
|
||||
3. **薪资计算错误**
|
||||
- 症状:绩效奖金计算结果不符合预期
|
||||
- 解决:验证绩效系数范围(0-5),检查考核得分
|
||||
|
||||
4. **关联查询性能问题**
|
||||
- 症状:员工列表加载缓慢
|
||||
- 解决:添加适当的索引,优化查询条件
|
||||
|
||||
**章节来源**
|
||||
- [staff.py](file://backend/app/api/v1/staff.py#L75-L78)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L104-L112)
|
||||
|
||||
## 结论
|
||||
|
||||
员工信息模型通过精心设计的数据结构和业务逻辑,为医院绩效管理系统提供了坚实的基础。该模型不仅满足了基本的员工信息管理需求,更重要的是通过完善的枚举类型、关系映射和约束机制,确保了数据的完整性和业务逻辑的正确性。
|
||||
|
||||
模型的关键优势包括:
|
||||
|
||||
1. **清晰的状态管理**:通过枚举类型明确员工状态,便于业务逻辑处理
|
||||
2. **灵活的薪资计算**:支持可调节的绩效系数,适应不同岗位的薪酬体系
|
||||
3. **完善的关联关系**:与科室、考核、工资等模块形成完整的业务闭环
|
||||
4. **严格的数据验证**:通过多种验证机制确保数据质量
|
||||
5. **良好的扩展性**:模块化设计便于后续功能扩展
|
||||
|
||||
该模型为整个系统的稳定运行奠定了坚实基础,是医院绩效管理不可或缺的重要组成部分。
|
||||
407
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/工资核算模型.md
Normal file
407
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/工资核算模型.md
Normal file
@@ -0,0 +1,407 @@
|
||||
# 工资核算模型
|
||||
|
||||
<cite>
|
||||
**本文引用的文件**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py)
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [backend/alembic/versions/001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [backend/alembic/versions/002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
- [frontend/src/views/salary/Salary.vue](file://frontend/src/views/salary/Salary.vue)
|
||||
- [frontend/src/api/salary.js](file://frontend/src/api/salary.js)
|
||||
- [docs/database.md](file://docs/database.md)
|
||||
- [docs/详细设计文档.md](file://docs/详细设计文档.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
本文档深入解析医院绩效系统中的工资核算模型,重点围绕SalaryRecord模型的设计理念、实现细节以及与考核系统的集成关系。文档涵盖以下关键内容:
|
||||
- 基本工资、绩效得分、绩效奖金、扣款补贴的计算逻辑
|
||||
- 工资核算的时间周期与状态管理(待处理、已确认)
|
||||
- 应发工资的计算公式与字段约束
|
||||
- 绩效奖金与绩效得分的关系、扣款与补贴的设置规则
|
||||
- 与员工的多对一关系、历史记录的版本控制
|
||||
- 批量核算的性能优化策略
|
||||
- 工资计算示例、异常处理机制与数据准确性验证方法
|
||||
|
||||
## 项目结构
|
||||
后端采用FastAPI + SQLAlchemy异步ORM架构,工资核算功能位于以下模块:
|
||||
- 模型层:定义SalaryRecord、Staff、Assessment等实体及其关系
|
||||
- 服务层:实现工资计算、生成、确认、批量处理等业务逻辑
|
||||
- API层:提供REST接口,支持按考核生成工资、批量生成与确认
|
||||
- 前端:提供工资记录查询、编辑、确认等界面
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "前端"
|
||||
FE_View["Salary.vue<br/>视图组件"]
|
||||
FE_API["salary.js<br/>API封装"]
|
||||
end
|
||||
subgraph "后端"
|
||||
API["salary.py<br/>API路由"]
|
||||
Service["salary_service.py<br/>服务层"]
|
||||
Model["models.py<br/>数据模型"]
|
||||
Schema["schemas.py<br/>数据模式"]
|
||||
DB["数据库<br/>salary_records表"]
|
||||
end
|
||||
FE_View --> FE_API
|
||||
FE_API --> API
|
||||
API --> Service
|
||||
Service --> Model
|
||||
Model --> DB
|
||||
Schema --> API
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L1-L156)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L1-L260)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [frontend/src/views/salary/Salary.vue](file://frontend/src/views/salary/Salary.vue#L33-L245)
|
||||
- [frontend/src/api/salary.js](file://frontend/src/api/salary.js#L1-L42)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L1-L156)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L1-L260)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [frontend/src/views/salary/Salary.vue](file://frontend/src/views/salary/Salary.vue#L33-L245)
|
||||
- [frontend/src/api/salary.js](file://frontend/src/api/salary.js#L1-L42)
|
||||
|
||||
## 核心组件
|
||||
- SalaryRecord模型:存储工资核算结果,包含基本工资、绩效得分、绩效奖金、扣款、补贴、应发工资与状态
|
||||
- Staff模型:员工基本信息与绩效系数,用于绩效奖金计算
|
||||
- Assessment模型:考核记录,提供加权得分作为绩效奖金依据
|
||||
- SalaryService服务:实现工资计算、生成、确认、批量处理等核心逻辑
|
||||
- API路由:提供查询、创建、更新、按考核生成、批量生成与确认等接口
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L149-L179)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L14-L260)
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L1-L156)
|
||||
|
||||
## 架构概览
|
||||
工资核算从考核结果出发,通过服务层计算绩效奖金并生成工资记录;前端提供查询与确认操作,后端通过权限控制确保只有管理员或经理可以进行关键操作。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as "客户端"
|
||||
participant API as "salary.py"
|
||||
participant Service as "salary_service.py"
|
||||
participant DB as "数据库"
|
||||
Client->>API : POST /salary/generate?staff_id&period_year&period_month
|
||||
API->>Service : generate_from_assessment(staff_id, year, month)
|
||||
Service->>DB : 查询员工信息(Staff)
|
||||
Service->>DB : 查询已确认考核(Assessment.status='finalized')
|
||||
Service->>Service : calculate_performance_bonus(weighted_score, performance_ratio)
|
||||
Service->>DB : 插入SalaryRecord(状态=pending)
|
||||
DB-->>Service : 返回新记录
|
||||
Service-->>API : 返回记录ID
|
||||
API-->>Client : {code,message,data : id}
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L96-L111)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L96-L111)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### SalaryRecord模型设计
|
||||
- 字段定义
|
||||
- 基本工资:base_salary,数值型,精度10位小数2位
|
||||
- 绩效得分:performance_score,数值型,精度5位小数2位
|
||||
- 绩效奖金:performance_bonus,数值型,精度10位小数2位
|
||||
- 扣款:deduction,数值型,精度10位小数2位
|
||||
- 补贴:allowance,数值型,精度10位小数2位
|
||||
- 应发工资:total_salary,数值型,精度10位小数2位
|
||||
- 状态:status,默认"pending"
|
||||
- 时间周期:period_year、period_month
|
||||
- 外键:staff_id,关联员工表
|
||||
- 约束与索引
|
||||
- 外键约束:staff_id -> staff.id
|
||||
- 索引:staff_id、(period_year, period_month)
|
||||
- 关系
|
||||
- 与Staff为多对一关系,支持反向访问salary_records
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+string title
|
||||
+float base_salary
|
||||
+float performance_ratio
|
||||
+string status
|
||||
+datetime hire_date
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+Assessment[] assessments
|
||||
+SalaryRecord[] salary_records
|
||||
}
|
||||
class SalaryRecord {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float base_salary
|
||||
+float performance_score
|
||||
+float performance_bonus
|
||||
+float deduction
|
||||
+float allowance
|
||||
+float total_salary
|
||||
+string status
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
}
|
||||
Staff "1" o-- "*" SalaryRecord : "多对一"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [backend/alembic/versions/001_initial.py](file://backend/alembic/versions/001_initial.py#L133-L154)
|
||||
- [docs/database.md](file://docs/database.md#L197-L216)
|
||||
- [docs/详细设计文档.md](file://docs/详细设计文档.md#L642-L662)
|
||||
|
||||
### 计算逻辑与公式
|
||||
- 绩效奖金计算
|
||||
- 公式:绩效奖金 = 绩效基数 × (绩效得分/100) × 绩效系数
|
||||
- 绩效基数:固定常量,服务层中定义
|
||||
- 绩效系数:来自员工表的performance_ratio
|
||||
- 应发工资计算
|
||||
- 公式:应发工资 = 基本工资 + 绩效奖金 + 补贴 - 扣款
|
||||
- 该公式在创建与更新工资记录时均会重新计算并持久化
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start(["开始"]) --> LoadStaff["加载员工信息<br/>获取base_salary, performance_ratio"]
|
||||
LoadStaff --> LoadAssessment["加载已确认考核<br/>获取weighted_score"]
|
||||
LoadAssessment --> CheckExisting{"是否存在同周期工资记录?"}
|
||||
CheckExisting --> |是| ReturnNone["返回空不重复生成"]
|
||||
CheckExisting --> |否| CalcBonus["计算绩效奖金<br/>bonus = 基数 × (score/100) × ratio"]
|
||||
CalcBonus --> CalcTotal["计算应发工资<br/>total = base + bonus + allowance - deduction"]
|
||||
CalcTotal --> CreateRecord["创建SalaryRecord<br/>状态=pending"]
|
||||
CreateRecord --> End(["结束"])
|
||||
ReturnNone --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L85-L91)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
|
||||
### 时间周期与状态管理
|
||||
- 时间周期
|
||||
- 由period_year与period_month共同构成,用于唯一标识某员工的某月工资记录
|
||||
- 数据库层面在salary_records上建立了复合索引(idx_salary_period),提升查询效率
|
||||
- 状态管理
|
||||
- 待处理:pending(默认状态)
|
||||
- 已确认:confirmed(管理员/经理确认后变更)
|
||||
- 已发放:paid(当前服务层未实现,但模型预留字段)
|
||||
- 状态变更流程
|
||||
- 单条确认:调用确认接口,仅当状态为pending时允许变更
|
||||
- 批量确认:按年月筛选pending状态记录,可选择按科室过滤
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 待处理
|
||||
待处理 --> 已确认 : "确认工资"
|
||||
已确认 --> 已发放 : "发放工资"
|
||||
已发放 --> [*]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L222-L231)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L234-L259)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L218-L219)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L222-L231)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L234-L259)
|
||||
|
||||
### 与员工的多对一关系与历史版本控制
|
||||
- 多对一关系
|
||||
- SalaryRecord.staff_id -> Staff.id,每个工资记录对应唯一员工
|
||||
- Staff.salary_records反向关系,支持按员工查询其历史工资记录
|
||||
- 历史版本控制
|
||||
- 当前版本未实现SalaryRecord的版本号字段;如需版本控制,可在模型中增加version字段并在更新时递增
|
||||
- 绩效计划的版本控制已在其他模型中实现(PerformancePlan.version),可借鉴其模式
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L108-L110)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L293-L293)
|
||||
|
||||
### 批量核算的性能优化
|
||||
- 批量生成
|
||||
- 服务层先查询指定科室下所有已确认的考核记录,再逐条生成工资记录
|
||||
- 建议在大规模数据场景下:
|
||||
- 使用分批处理(分页查询考核记录)
|
||||
- 异步并发插入(注意数据库连接池与事务边界)
|
||||
- 增加数据库索引覆盖查询条件
|
||||
- 批量确认
|
||||
- 通过SQL查询一次性筛选出待确认记录,减少多次往返
|
||||
- 支持按科室过滤,缩小确认范围
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L192-L219)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L234-L259)
|
||||
|
||||
### 扣款与补贴的设置规则
|
||||
- 扣款与补贴均为数值型字段,支持在创建或更新时设置
|
||||
- 服务层在创建与更新时均会重新计算应发工资:total_salary = base_salary + performance_bonus + allowance - deduction
|
||||
- 建议在业务层增加校验规则:
|
||||
- 扣款与补贴必须非负
|
||||
- 应发工资计算后可进行合理性校验(如不得为负)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L85-L91)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L114-L120)
|
||||
|
||||
### 绩效奖金与绩效得分的关系
|
||||
- 绩效奖金 = 绩效基数 × (绩效得分/100) × 绩效系数
|
||||
- 绩效得分来自Assessment.weighted_score,状态必须为"finalized"
|
||||
- 绩效系数来自Staff.performance_ratio,不同岗位/级别可设置不同系数
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L143-L153)
|
||||
|
||||
### API与前端交互
|
||||
- API接口
|
||||
- 列表查询:支持按员工、科室、年份、月份、状态筛选
|
||||
- 详情查询:返回带员工与科室名称的完整信息
|
||||
- 创建/更新:仅允许在待处理状态下更新
|
||||
- 按考核生成:基于已确认考核自动生成工资记录
|
||||
- 批量生成/确认:支持按科室批量生成与批量确认
|
||||
- 前端展示
|
||||
- 列表显示基本工资、绩效得分、绩效奖金、补贴、扣款、应发工资等字段
|
||||
- 提供编辑弹窗,支持更新扣款、补贴、备注等
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L20-L156)
|
||||
- [frontend/src/views/salary/Salary.vue](file://frontend/src/views/salary/Salary.vue#L33-L245)
|
||||
- [frontend/src/api/salary.js](file://frontend/src/api/salary.js#L1-L42)
|
||||
|
||||
## 依赖分析
|
||||
- 模型依赖
|
||||
- SalaryRecord依赖Staff(外键)
|
||||
- Assessment与SalaryRecord通过staff_id间接关联
|
||||
- 服务层依赖
|
||||
- 依赖Staff、Assessment模型进行数据查询与计算
|
||||
- 依赖Pydantic模式进行请求/响应数据校验
|
||||
- API层依赖
|
||||
- 依赖Security中间件进行权限控制(管理员/经理)
|
||||
- 依赖数据库会话进行异步操作
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
SalaryRecord["SalaryRecord模型"] --> Staff["Staff模型"]
|
||||
SalaryService["SalaryService"] --> SalaryRecord
|
||||
SalaryService --> Staff
|
||||
SalaryService --> Assessment["Assessment模型"]
|
||||
API["salary.py"] --> SalaryService
|
||||
API --> Schema["schemas.py"]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L149-L179)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L10-L11)
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L14-L15)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L231)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L115)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L149-L179)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L10-L11)
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L14-L15)
|
||||
|
||||
## 性能考虑
|
||||
- 查询优化
|
||||
- salary_records表已建立索引:staff_id、(period_year, period_month)
|
||||
- API层使用selectinload预加载关联对象,避免N+1查询
|
||||
- 批量处理
|
||||
- 批量生成与确认采用SQL查询一次性筛选,减少循环调用
|
||||
- 建议在高并发场景下增加数据库连接池配置与事务隔离级别
|
||||
- 数据类型
|
||||
- 使用Numeric类型保证金额精度,避免浮点误差累积
|
||||
|
||||
[本节为通用性能建议,无需特定文件来源]
|
||||
|
||||
## 故障排除指南
|
||||
- 无法生成工资
|
||||
- 检查是否存在已确认的考核记录且状态为"finalized"
|
||||
- 检查是否已存在同周期的工资记录(防止重复生成)
|
||||
- 无法确认工资
|
||||
- 确认记录状态必须为"pending"
|
||||
- 检查权限:仅管理员或经理可执行确认操作
|
||||
- 数据不一致
|
||||
- 更新扣款/补贴后需重新计算应发工资
|
||||
- 核对数据库索引是否生效,避免查询性能问题
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L155-L164)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L224-L226)
|
||||
- [backend/app/api/v1/salary.py](file://backend/app/api/v1/salary.py#L132-L142)
|
||||
|
||||
## 结论
|
||||
SalaryRecord模型通过清晰的字段设计与严格的计算逻辑,实现了从考核到工资的自动化流转。服务层提供了完善的生成、确认与批量处理能力,并通过索引与预加载优化了查询性能。未来可在版本控制、状态扩展(如已发放)与更细粒度的扣款/补贴规则方面进一步增强。
|
||||
|
||||
[本节为总结性内容,无需特定文件来源]
|
||||
|
||||
## 附录
|
||||
|
||||
### 工资计算示例
|
||||
- 输入
|
||||
- 员工:基本工资=10000,绩效系数=1.2
|
||||
- 考核:加权得分=95
|
||||
- 扣款=0,补贴=500
|
||||
- 计算过程
|
||||
- 绩效奖金 = 固定基数 × (95/100) × 1.2
|
||||
- 应发工资 = 10000 + 绩效奖金 + 500 - 0
|
||||
- 输出
|
||||
- 工资记录状态=pending,等待确认
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L71-L74)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L172-L173)
|
||||
|
||||
### 数据准确性验证方法
|
||||
- 金额精度:使用Numeric类型,避免浮点误差
|
||||
- 业务规则:在服务层增加校验(扣款/补贴非负、应发工资合理)
|
||||
- 索引验证:确认salary_records索引生效,提升查询性能
|
||||
- 测试覆盖:编写单元测试验证计算逻辑与状态变更流程
|
||||
|
||||
**章节来源**
|
||||
- [backend/alembic/versions/001_initial.py](file://backend/alembic/versions/001_initial.py#L133-L154)
|
||||
- [backend/app/services/salary_service.py](file://backend/app/services/salary_service.py#L85-L91)
|
||||
545
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/核心数据模型.md
Normal file
545
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/核心数据模型.md
Normal file
@@ -0,0 +1,545 @@
|
||||
# 核心数据模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [finance.py](file://backend/app/models/finance.py)
|
||||
- [database.py](file://backend/app/core/database.py)
|
||||
- [init_db.py](file://backend/app/core/init_db.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py)
|
||||
- [database.md](file://docs/database.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
|
||||
本文件详细阐述医院绩效系统的核心数据模型设计,重点涵盖Department(科室)、Staff(员工)、Assessment(考核记录)、AssessmentDetail(考核明细)、SalaryRecord(工资核算记录)等核心业务模型。文档从设计理念、实现细节、字段定义、数据类型、约束条件、业务规则、模型关联关系、索引设计、性能优化策略等多个维度进行全面解析,并提供使用示例和最佳实践指导。
|
||||
|
||||
## 项目结构
|
||||
|
||||
该系统采用分层架构,核心模型位于 `backend/app/models/` 目录,数据库连接通过 `backend/app/core/database.py` 管理,初始化逻辑在 `backend/app/core/init_db.py` 中实现。数据验证通过 Pydantic 模式在 `backend/app/schemas/schemas.py` 中定义,服务层负责业务逻辑处理。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "模型层"
|
||||
M1[models.py<br/>核心业务模型]
|
||||
M2[finance.py<br/>财务核算模型]
|
||||
end
|
||||
subgraph "核心配置"
|
||||
C1[database.py<br/>数据库连接]
|
||||
C2[init_db.py<br/>数据库初始化]
|
||||
end
|
||||
subgraph "数据验证"
|
||||
S1[schemas.py<br/>Pydantic模式]
|
||||
end
|
||||
subgraph "服务层"
|
||||
SV1[staff_service.py]
|
||||
SV2[assessment_service.py]
|
||||
SV3[salary_service.py]
|
||||
end
|
||||
M1 --> C1
|
||||
M2 --> C1
|
||||
C2 --> M1
|
||||
S1 --> SV1
|
||||
S1 --> SV2
|
||||
S1 --> SV3
|
||||
SV1 --> M1
|
||||
SV2 --> M1
|
||||
SV3 --> M1
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L231)
|
||||
- [finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
- [database.py](file://backend/app/core/database.py#L9-L25)
|
||||
- [init_db.py](file://backend/app/core/init_db.py#L1-L115)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [finance.py](file://backend/app/models/finance.py#L1-L79)
|
||||
- [database.py](file://backend/app/core/database.py#L1-L39)
|
||||
- [init_db.py](file://backend/app/core/init_db.py#L1-L115)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
## 核心组件
|
||||
|
||||
本节概述五个核心业务模型的设计理念和实现要点:
|
||||
|
||||
### Department(科室)
|
||||
- 设计理念:支持多层级组织架构,通过自关联实现父子关系
|
||||
- 关键特性:科室类型枚举、层级管理、排序机制、激活状态控制
|
||||
- 外键关系:自关联 parent_id 指向自身,children 反向关系
|
||||
- 索引设计:按科室类型和父级ID建立索引
|
||||
|
||||
### Staff(员工)
|
||||
- 设计理念:员工与科室的一对多关系,支持多种状态管理
|
||||
- 关键特性:工号唯一性、基本工资和绩效系数、状态枚举
|
||||
- 外键关系:department_id 指向 Department,一对多关系
|
||||
- 索引设计:按科室ID和状态建立复合索引
|
||||
|
||||
### Assessment(考核记录)
|
||||
- 设计理念:支持多周期、多状态的考核流程管理
|
||||
- 关键特性:总分和加权得分计算、多角色参与(考核人、审核人)
|
||||
- 外键关系:staff_id 指向 Staff,assessor_id 和 reviewer_id 自关联
|
||||
- 索引设计:按员工ID、考核周期、状态建立复合索引
|
||||
|
||||
### AssessmentDetail(考核明细)
|
||||
- 设计理念:一对一关联 Assessment,支持多指标明细记录
|
||||
- 关键特性:实际值和得分记录、佐证材料管理
|
||||
- 外键关系:assessment_id 和 indicator_id 的双向关联
|
||||
- 索引设计:按考核记录ID和指标ID建立索引
|
||||
|
||||
### SalaryRecord(工资核算记录)
|
||||
- 设计理念:基于考核结果的自动化工资核算
|
||||
- 关键特性:基本工资、绩效奖金、扣款、补贴的统一管理
|
||||
- 外键关系:staff_id 指向 Staff
|
||||
- 索引设计:按员工ID和考核周期建立复合索引
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L231)
|
||||
- [database.md](file://docs/database.md#L99-L216)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用分层架构,核心数据模型通过 SQLAlchemy ORM 映射到数据库表,配合 Pydantic 模式进行数据验证,服务层封装业务逻辑。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+DeptType dept_type
|
||||
+int parent_id
|
||||
+int level
|
||||
+int sort_order
|
||||
+bool is_active
|
||||
+string description
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+children : List[Department]
|
||||
+staff : List[Staff]
|
||||
}
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+string title
|
||||
+string phone
|
||||
+string email
|
||||
+float base_salary
|
||||
+float performance_ratio
|
||||
+StaffStatus status
|
||||
+datetime hire_date
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+department : Department
|
||||
+assessments : List[Assessment]
|
||||
+salary_records : List[SalaryRecord]
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+string period_type
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentStatus status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+staff : Staff
|
||||
+assessor : Staff
|
||||
+reviewer : Staff
|
||||
+details : List[AssessmentDetail]
|
||||
}
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+string evidence
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+assessment : Assessment
|
||||
+indicator : Indicator
|
||||
}
|
||||
class SalaryRecord {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float base_salary
|
||||
+float performance_score
|
||||
+float performance_bonus
|
||||
+float deduction
|
||||
+float allowance
|
||||
+float total_salary
|
||||
+string status
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+staff : Staff
|
||||
}
|
||||
Department "1" <-- "N" Staff : "一对多"
|
||||
Staff "1" <-- "N" Assessment : "一对多"
|
||||
Assessment "1" <-- "N" AssessmentDetail : "一对多"
|
||||
Staff "1" <-- "N" SalaryRecord : "一对多"
|
||||
Assessment "N" --> "1" Staff : "多对一"
|
||||
AssessmentDetail "N" --> "1" Assessment : "多对一"
|
||||
AssessmentDetail "N" --> "1" Indicator : "多对一"
|
||||
SalaryRecord "N" --> "1" Staff : "多对一"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L231)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### Department(科室)模型
|
||||
|
||||
#### 字段定义与数据类型
|
||||
- id: 主键,整数类型,自动递增
|
||||
- name: 科室名称,字符串类型,最大长度100,必填
|
||||
- code: 科室编码,字符串类型,最大长度20,唯一且必填
|
||||
- dept_type: 科室类型枚举,支持临床、医技、医辅、行政、后勤等类型
|
||||
- parent_id: 上级科室ID,整数类型,自关联外键
|
||||
- level: 层级,整数类型,默认1,范围1-5
|
||||
- sort_order: 排序,整数类型,默认0
|
||||
- is_active: 是否启用,布尔类型,默认True
|
||||
- description: 描述信息,文本类型
|
||||
- created_at/updated_at: 时间戳,自动维护
|
||||
|
||||
#### 约束条件与业务规则
|
||||
- 唯一性约束:code 字段唯一
|
||||
- 枚举约束:dept_type 必须属于预定义类型集合
|
||||
- 自关联约束:parent_id 引用自身主键
|
||||
- 层级限制:level 范围1-5
|
||||
|
||||
#### 关联关系
|
||||
- 一对多:Department → Staff(children)
|
||||
- 自关联:parent_id → Department(parent)
|
||||
|
||||
#### 索引设计
|
||||
- idx_dept_type:按科室类型查询优化
|
||||
- idx_dept_parent:按父级科室查询优化
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L86)
|
||||
- [database.md](file://docs/database.md#L99-L115)
|
||||
|
||||
### Staff(员工)模型
|
||||
|
||||
#### 字段定义与数据类型
|
||||
- id: 主键,整数类型,自动递增
|
||||
- employee_id: 工号,字符串类型,最大长度20,唯一且必填
|
||||
- name: 姓名,字符串类型,最大长度50,必填
|
||||
- department_id: 所属科室ID,整数类型,外键约束
|
||||
- position: 职位,字符串类型,最大长度50,必填
|
||||
- title: 职称,字符串类型,最大长度50
|
||||
- phone/email: 联系方式,字符串类型
|
||||
- base_salary: 基本工资,数值类型,精度10,2,默认0
|
||||
- performance_ratio: 绩效系数,数值类型,精度5,2,默认1.0,范围0-5
|
||||
- status: 员工状态枚举,默认active
|
||||
- hire_date: 入职日期,日期时间类型
|
||||
- created_at/updated_at: 时间戳
|
||||
|
||||
#### 约束条件与业务规则
|
||||
- 唯一性约束:employee_id 唯一
|
||||
- 数值范围约束:performance_ratio 范围0-5
|
||||
- 外键约束:department_id 引用 Department.id
|
||||
- 状态枚举:仅允许预定义状态值
|
||||
|
||||
#### 关联关系
|
||||
- 多对一:Staff → Department(department)
|
||||
- 一对多:Department → Staff(staff)
|
||||
- 一对多:Staff → Assessment(assessments)
|
||||
- 一对多:Staff → SalaryRecord(salary_records)
|
||||
|
||||
#### 索引设计
|
||||
- idx_staff_dept:按科室ID查询优化
|
||||
- idx_staff_status:按状态查询优化
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L88-L114)
|
||||
- [database.md](file://docs/database.md#L117-L136)
|
||||
|
||||
### Assessment(考核记录)模型
|
||||
|
||||
#### 字段定义与数据类型
|
||||
- id: 主键,整数类型,自动递增
|
||||
- staff_id: 员工ID,整数类型,外键约束
|
||||
- period_year: 考核年度,整数类型,必填
|
||||
- period_month: 考核月份,整数类型,必填
|
||||
- period_type: 考核周期类型,字符串类型,默认monthly
|
||||
- total_score: 总分,数值类型,精度5,2,默认0
|
||||
- weighted_score: 加权得分,数值类型,精度5,2,默认0
|
||||
- status: 考核状态枚举,默认draft
|
||||
- assessor_id/reviewer_id: 考核人/审核人ID,整数类型,自关联外键
|
||||
- submit_time/review_time: 提交/审核时间,日期时间类型
|
||||
- remark: 备注,文本类型
|
||||
- created_at/updated_at: 时间戳
|
||||
|
||||
#### 约束条件与业务规则
|
||||
- 外键约束:staff_id 引用 Staff.id
|
||||
- 自关联约束:assessor_id/reviewer_id 引用 Staff.id
|
||||
- 状态枚举:支持草稿、提交、审核、确认、驳回等状态
|
||||
- 计算规则:total_score 为明细得分之和,weighted_score 为按指标权重加权
|
||||
|
||||
#### 关联关系
|
||||
- 多对一:Assessment → Staff(staff)
|
||||
- 多对一:Assessment → Staff(assessor)
|
||||
- 多对一:Assessment → Staff(reviewer)
|
||||
- 一对多:Assessment → AssessmentDetail(details)
|
||||
- 级联删除:details 支持级联删除
|
||||
|
||||
#### 索引设计
|
||||
- idx_assessment_staff:按员工ID查询优化
|
||||
- idx_assessment_period:按考核周期查询优化
|
||||
- idx_assessment_status:按状态查询优化
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [database.md](file://docs/database.md#L159-L179)
|
||||
|
||||
### AssessmentDetail(考核明细)模型
|
||||
|
||||
#### 字段定义与数据类型
|
||||
- id: 主键,整数类型,自动递增
|
||||
- assessment_id: 考核记录ID,整数类型,外键约束
|
||||
- indicator_id: 指标ID,整数类型,外键约束
|
||||
- actual_value: 实际值,数值类型,精度10,2
|
||||
- score: 得分,数值类型,精度5,2,默认0
|
||||
- evidence: 佐证材料,文本类型
|
||||
- remark: 备注,文本类型
|
||||
- created_at/updated_at: 时间戳
|
||||
|
||||
#### 约束条件与业务规则
|
||||
- 外键约束:assessment_id 引用 Assessment.id,indicator_id 引用 Indicator.id
|
||||
- 计算规则:Assessment.total_score = Σ(AssessmentDetail.score)
|
||||
|
||||
#### 关联关系
|
||||
- 多对一:AssessmentDetail → Assessment(assessment)
|
||||
- 多对一:AssessmentDetail → Indicator(indicator)
|
||||
|
||||
#### 索引设计
|
||||
- idx_detail_assessment:按考核记录ID查询优化
|
||||
- idx_detail_indicator:按指标ID查询优化
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L181-L202)
|
||||
- [database.md](file://docs/database.md#L181-L195)
|
||||
|
||||
### SalaryRecord(工资核算记录)模型
|
||||
|
||||
#### 字段定义与数据类型
|
||||
- id: 主键,整数类型,自动递增
|
||||
- staff_id: 员工ID,整数类型,外键约束
|
||||
- period_year: 年度,整数类型,必填
|
||||
- period_month: 月份,整数类型,必填
|
||||
- base_salary: 基本工资,数值类型,精度10,2,默认0
|
||||
- performance_score: 绩效得分,数值类型,精度5,2,默认0
|
||||
- performance_bonus: 绩效奖金,数值类型,精度10,2,默认0
|
||||
- deduction: 扣款,数值类型,精度10,2,默认0
|
||||
- allowance: 补贴,数值类型,精度10,2,默认0
|
||||
- total_salary: 应发工资,数值类型,精度10,2,默认0
|
||||
- status: 状态,默认pending
|
||||
- remark: 备注,文本类型
|
||||
- created_at/updated_at: 时间戳
|
||||
|
||||
#### 约束条件与业务规则
|
||||
- 外键约束:staff_id 引用 Staff.id
|
||||
- 计算规则:total_salary = base_salary + performance_bonus + allowance - deduction
|
||||
- 状态管理:支持pending、confirmed、paid等状态
|
||||
|
||||
#### 关联关系
|
||||
- 多对一:SalaryRecord → Staff(staff)
|
||||
|
||||
#### 索引设计
|
||||
- idx_salary_staff:按员工ID查询优化
|
||||
- idx_salary_period:按考核周期查询优化
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L205-L230)
|
||||
- [database.md](file://docs/database.md#L197-L216)
|
||||
|
||||
### 数据验证规则
|
||||
|
||||
系统采用 Pydantic 模式进行数据验证,确保输入数据的完整性和正确性:
|
||||
|
||||
#### 员工数据验证
|
||||
- employee_id: 长度不超过20字符,必填
|
||||
- base_salary: 非负数,最小值0
|
||||
- performance_ratio: 范围0-5
|
||||
- name/position/title: 长度限制和必填约束
|
||||
|
||||
#### 考核数据验证
|
||||
- period_year: 范围2020-2100
|
||||
- period_month: 范围1-12
|
||||
- score: 非负数,最小值0
|
||||
|
||||
#### 工资数据验证
|
||||
- 所有金额字段:非负数约束
|
||||
- 计算字段:自动计算,不允许直接修改
|
||||
|
||||
**章节来源**
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L107-L149)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L220-L271)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L274-L311)
|
||||
|
||||
## 依赖分析
|
||||
|
||||
系统模型间存在清晰的依赖关系,遵循数据库规范化原则:
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
A[Department] --> B[Staff]
|
||||
B --> C[Assessment]
|
||||
C --> D[AssessmentDetail]
|
||||
B --> E[SalaryRecord]
|
||||
C -.-> F[Indicator]
|
||||
G[Assessment] -.自关联.-> B
|
||||
H[AssessmentDetail] -.多对一.-> F
|
||||
subgraph "索引优化"
|
||||
I[idx_dept_type]
|
||||
J[idx_staff_dept]
|
||||
K[idx_assessment_staff]
|
||||
L[idx_detail_assessment]
|
||||
M[idx_salary_staff]
|
||||
end
|
||||
A -.-> I
|
||||
B -.-> J
|
||||
C -.-> K
|
||||
D -.-> L
|
||||
E -.-> M
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L231)
|
||||
- [database.md](file://docs/database.md#L99-L216)
|
||||
|
||||
### 外键约束与级联操作
|
||||
|
||||
- Assessment → AssessmentDetail: 级联删除(delete-orphan)
|
||||
- Department → Staff: 一对多关系
|
||||
- Staff → Assessment: 一对多关系
|
||||
- Staff → SalaryRecord: 一对多关系
|
||||
|
||||
### 性能优化策略
|
||||
|
||||
#### 查询优化
|
||||
- 使用复合索引优化常用查询条件
|
||||
- 通过 selectinload 减少 N+1 查询问题
|
||||
- 分页查询避免大数据集加载
|
||||
|
||||
#### 数据库连接
|
||||
- 异步数据库连接提高并发性能
|
||||
- 连接池管理优化资源使用
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L173-L173)
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L26-L49)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L29-L55)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L32-L58)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 索引策略
|
||||
- 单列索引:按枚举类型、状态、激活状态快速过滤
|
||||
- 复合索引:按员工ID+状态、考核周期、科室ID+状态等组合查询优化
|
||||
|
||||
### 查询优化
|
||||
- 使用 selectinload 预加载关联数据
|
||||
- 分页查询限制结果集大小
|
||||
- 条件查询精确匹配减少扫描范围
|
||||
|
||||
### 缓存策略
|
||||
- 频繁访问的枚举类型缓存
|
||||
- 常用查询结果短期缓存
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题与解决方案
|
||||
|
||||
#### 数据重复错误
|
||||
- 症状:插入重复的工号或科室编码
|
||||
- 解决:检查唯一性约束,使用去重逻辑
|
||||
|
||||
#### 外键约束错误
|
||||
- 症状:插入不存在的员工或科室ID
|
||||
- 解决:先创建关联实体,再创建子实体
|
||||
|
||||
#### 数据验证失败
|
||||
- 症状:字段超出范围或格式不正确
|
||||
- 解决:检查 Pydantic 模式的验证规则
|
||||
|
||||
#### 性能问题
|
||||
- 症状:查询响应缓慢
|
||||
- 解决:检查索引使用情况,优化查询条件
|
||||
|
||||
**章节来源**
|
||||
- [init_db.py](file://backend/app/core/init_db.py#L12-L115)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L107-L149)
|
||||
|
||||
## 结论
|
||||
|
||||
本核心数据模型设计充分体现了医院绩效管理的业务需求,通过清晰的实体关系、严格的约束条件、完善的索引策略和合理的性能优化,为系统的稳定运行提供了坚实基础。模型间的层次化设计支持复杂的组织架构,灵活的状态管理适应不同的业务流程,而完善的验证机制确保了数据质量。
|
||||
|
||||
## 附录
|
||||
|
||||
### 模型使用示例
|
||||
|
||||
#### 创建员工
|
||||
```python
|
||||
# 通过服务层创建员工
|
||||
staff = await StaffService.create(db, staff_data)
|
||||
```
|
||||
|
||||
#### 创建考核记录
|
||||
```python
|
||||
# 通过服务层创建考核
|
||||
assessment = await AssessmentService.create(db, assessment_data)
|
||||
```
|
||||
|
||||
#### 生成工资记录
|
||||
```python
|
||||
# 基于考核结果生成工资
|
||||
salary_record = await SalaryService.generate_from_assessment(db, staff_id, year, month)
|
||||
```
|
||||
|
||||
### 最佳实践
|
||||
|
||||
1. **数据完整性**:始终使用 Pydantic 模式进行数据验证
|
||||
2. **事务管理**:在复杂操作中使用数据库事务保证一致性
|
||||
3. **索引优化**:根据查询模式合理创建索引
|
||||
4. **错误处理**:完善异常处理和回滚机制
|
||||
5. **性能监控**:定期分析慢查询日志优化性能
|
||||
|
||||
**章节来源**
|
||||
- [staff_service.py](file://backend/app/services/staff_service.py#L70-L91)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
- [salary_service.py](file://backend/app/services/salary_service.py#L127-L190)
|
||||
453
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/科室信息模型.md
Normal file
453
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/科室信息模型.md
Normal file
@@ -0,0 +1,453 @@
|
||||
# 科室信息模型
|
||||
|
||||
<cite>
|
||||
**本文引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py)
|
||||
- [department_service.py](file://backend/app/services/department_service.py)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue)
|
||||
- [department.js](file://frontend/src/api/department.js)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考量](#性能考量)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
本文档系统化阐述“科室信息模型”的设计理念与实现细节,围绕 Department 模型展开,涵盖:
|
||||
- 科室类型枚举(DeptType)及其业务分类
|
||||
- 树形层级结构与父子关系设计
|
||||
- 字段语义、数据类型、约束条件与业务规则
|
||||
- 科室编码唯一性、层级计算逻辑、排序机制与状态管理
|
||||
- 科室类型分类的应用场景与最佳实践
|
||||
- 数据操作示例、层级查询方法与常见问题排查
|
||||
|
||||
## 项目结构
|
||||
后端采用分层架构:API 层负责请求处理与鉴权,Service 层封装业务逻辑,Model 层定义数据模型与数据库映射;前端通过 API 模块调用后端接口,实现科室数据的增删改查与树形展示。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "前端"
|
||||
FE_Dialog["Departments.vue<br/>新增/编辑/删除/树形选择"]
|
||||
FE_API["department.js<br/>HTTP 请求封装"]
|
||||
end
|
||||
subgraph "后端"
|
||||
API["departments.py<br/>FastAPI 路由"]
|
||||
SVC["department_service.py<br/>业务逻辑"]
|
||||
MODEL["models.py<br/>Department 模型与 DeptType 枚举"]
|
||||
end
|
||||
FE_Dialog --> FE_API
|
||||
FE_API --> API
|
||||
API --> SVC
|
||||
SVC --> MODEL
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L1-L108)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L1-L150)
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L103-L272)
|
||||
- [department.js](file://frontend/src/api/department.js#L1-L32)
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L64-L103)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L1-L108)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L1-L150)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L1-L290)
|
||||
- [department.js](file://frontend/src/api/department.js#L1-L32)
|
||||
|
||||
## 核心组件
|
||||
- Department 模型:定义科室实体的字段、索引与关系
|
||||
- DeptType 枚举:标准化科室类型,支持多类业务场景
|
||||
- DepartmentService:封装 CRUD、层级树构建与校验逻辑
|
||||
- FastAPI 路由:提供列表、树形、详情、创建、更新、删除等接口
|
||||
- 前端视图与 API:提供交互界面与 HTTP 请求封装
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L16-L26)
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L13-L149)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L20-L107)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L64-L103)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L103-L272)
|
||||
- [department.js](file://frontend/src/api/department.js#L1-L32)
|
||||
|
||||
## 架构概览
|
||||
后端采用 ORM 映射,Department 通过外键维护自引用的父子关系;Service 层在创建时自动计算层级,API 层提供树形结构查询与分页列表查询。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Department {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+DeptType dept_type
|
||||
+int? parent_id
|
||||
+int level
|
||||
+int sort_order
|
||||
+bool is_active
|
||||
+string? description
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+parent : Department?
|
||||
+children : Department[]
|
||||
+staff : Staff[]
|
||||
}
|
||||
class DepartmentService {
|
||||
+get_list(...)
|
||||
+get_by_id(...)
|
||||
+get_by_code(...)
|
||||
+create(...)
|
||||
+update(...)
|
||||
+delete(...)
|
||||
+get_tree(...)
|
||||
}
|
||||
class DeptType {
|
||||
<<enumeration>>
|
||||
+CLINICAL_SURGICAL
|
||||
+CLINICAL_NONSURGICAL_WARD
|
||||
+CLINICAL_NONSURGICAL_NOWARD
|
||||
+MEDICAL_TECH
|
||||
+MEDICAL_AUXILIARY
|
||||
+NURSING
|
||||
+ADMIN
|
||||
+FINANCE
|
||||
+LOGISTICS
|
||||
}
|
||||
DepartmentService --> Department : "操作"
|
||||
Department --> DeptType : "使用"
|
||||
Department --> Department : "自引用父子关系"
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [models.py](file://backend/app/models/models.py#L16-L26)
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L13-L149)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### Department 模型与字段规范
|
||||
- 主键与标识
|
||||
- id:整型,自增主键
|
||||
- code:字符串,长度限制,唯一约束,用于业务识别与去重
|
||||
- 基础信息
|
||||
- name:字符串,长度限制,必填
|
||||
- description:文本,可空
|
||||
- 组织结构
|
||||
- parent_id:外键指向同表 id,支持树形层级
|
||||
- level:整型,默认 1,表示层级深度
|
||||
- sort_order:整型,默认 0,用于排序
|
||||
- 类型与状态
|
||||
- dept_type:枚举 DeptType,必填
|
||||
- is_active:布尔,默认启用
|
||||
- 时间戳
|
||||
- created_at、updated_at:自动维护
|
||||
- 索引与关系
|
||||
- 索引:按类型、父节点
|
||||
- 关系:parent(反向 children)、staff(一对多)
|
||||
|
||||
字段约束与业务规则
|
||||
- 唯一性:code 唯一,API 层在创建前进行重复校验
|
||||
- 层级计算:创建时若指定 parent_id,则 level = 父级 level + 1;否则默认 1
|
||||
- 排序:列表与树形查询均按 sort_order 与 id 排序
|
||||
- 状态:is_active 控制启用/停用,影响列表过滤与前端显示
|
||||
- 父子关系:支持任意层级的树形组织,删除时需确保无子节点
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L62-L78)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L74-L77)
|
||||
|
||||
### 科室类型枚举(DeptType)
|
||||
- 分类与含义
|
||||
- 手术临床:clinical_surgical
|
||||
- 非手术有病房:clinical_nonsurgical_ward
|
||||
- 非手术无病房:clinical_nonsurgical_noward
|
||||
- 医技:medical_tech
|
||||
- 医辅:medical_auxiliary
|
||||
- 护理:nursing
|
||||
- 行政:admin
|
||||
- 财务:finance
|
||||
- 后勤:logistics
|
||||
- 应用场景
|
||||
- 指标模板匹配:不同类型科室适用不同指标集合
|
||||
- 权限与菜单:类型决定可访问的功能范围
|
||||
- 报表与统计:按类型聚合绩效、财务等数据
|
||||
- 计划与考核:类型驱动 KPI 设定与权重分配
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L16-L26)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L12-L21)
|
||||
|
||||
### 树形层级结构与父子关系
|
||||
- 自引用关系
|
||||
- Department.parent_id 外键指向 Department.id
|
||||
- 通过 relationship 建立 parent 与 children 的双向关系
|
||||
- 层级计算
|
||||
- 创建时根据 parent_id 查询父级 level 并 +1
|
||||
- 支持多级嵌套,level 从 1 开始
|
||||
- 树形构建
|
||||
- Service 层一次性查询所有科室,按 sort_order 与 id 排序
|
||||
- 使用字典映射与父子映射构建树根集
|
||||
- 避免懒加载导致的循环依赖与性能问题
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start(["开始"]) --> LoadDepts["查询所有科室<br/>按 sort_order,id 排序"]
|
||||
LoadDepts --> BuildMap["构建 id->节点 映射"]
|
||||
BuildMap --> Iterate["遍历科室列表"]
|
||||
Iterate --> HasParent{"存在 parent_id 且父节点在映射中?"}
|
||||
HasParent --> |是| AppendChild["将当前节点加入父节点 children"]
|
||||
HasParent --> |否| AddRoot["加入根节点集"]
|
||||
AppendChild --> Next["下一个科室"]
|
||||
AddRoot --> Next
|
||||
Next --> Done(["返回根节点树"])
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L149)
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L78-L80)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L149)
|
||||
|
||||
### 数据操作流程与最佳实践
|
||||
|
||||
#### 列表查询
|
||||
- 参数:dept_type(可选)、is_active(可选)、page、page_size
|
||||
- 排序:sort_order → id
|
||||
- 返回:分页结果与总数
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant FE as "前端"
|
||||
participant API as "departments.py"
|
||||
participant SVC as "department_service.py"
|
||||
participant DB as "数据库"
|
||||
FE->>API : GET /departments?page=&page_size=&dept_type=&is_active=
|
||||
API->>SVC : get_list(dept_type,is_active,page,page_size)
|
||||
SVC->>DB : select(department) + where + order_by + limit/offset
|
||||
DB-->>SVC : 列表数据
|
||||
SVC->>DB : count(*) 子查询
|
||||
DB-->>SVC : 总数
|
||||
SVC-->>API : (列表,总数)
|
||||
API-->>FE : JSON 响应
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L20-L40)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L17-L43)
|
||||
|
||||
章节来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L20-L40)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L17-L43)
|
||||
|
||||
#### 树形查询
|
||||
- 参数:dept_type(可选)
|
||||
- 排序:sort_order → id
|
||||
- 返回:根节点树,支持前端树形选择器
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant FE as "前端"
|
||||
participant API as "departments.py"
|
||||
participant SVC as "department_service.py"
|
||||
participant DB as "数据库"
|
||||
FE->>API : GET /departments/tree?dept_type=
|
||||
API->>SVC : get_tree(dept_type)
|
||||
SVC->>DB : select(department) + order_by(sort_order,id)
|
||||
DB-->>SVC : 所有科室
|
||||
SVC->>SVC : 构建 id->节点 映射
|
||||
SVC->>SVC : 追加到父节点 children 或根集
|
||||
SVC-->>API : 根节点树
|
||||
API-->>FE : JSON 响应
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L43-L51)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L149)
|
||||
|
||||
章节来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L43-L51)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L113-L149)
|
||||
|
||||
#### 创建科室
|
||||
- 前端校验:必填项(编码、名称、类型)
|
||||
- 服务端校验:编码唯一性
|
||||
- 层级计算:若 parent_id 存在则 level = 父级 level + 1
|
||||
- 返回:完整 Department 对象
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant FE as "前端"
|
||||
participant API as "departments.py"
|
||||
participant SVC as "department_service.py"
|
||||
participant DB as "数据库"
|
||||
FE->>API : POST /departments
|
||||
API->>SVC : get_by_code(code)
|
||||
SVC->>DB : select(code)
|
||||
DB-->>SVC : 结果
|
||||
SVC-->>API : 若存在则抛错
|
||||
API->>SVC : create(dept_data)
|
||||
SVC->>SVC : 计算 level(parent.level+1)
|
||||
SVC->>DB : insert(department)
|
||||
DB-->>SVC : 新记录
|
||||
SVC-->>API : 返回新建对象
|
||||
API-->>FE : JSON 响应
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L67-L80)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L62-L78)
|
||||
|
||||
章节来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L67-L80)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L62-L78)
|
||||
|
||||
#### 更新与删除
|
||||
- 更新:支持修改名称、类型、父级、排序、状态、描述
|
||||
- 删除:若存在子节点则拒绝删除,避免破坏树形结构
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
UStart(["更新入口"]) --> GetByID["根据 id 查询科室"]
|
||||
GetByID --> Exists{"是否存在?"}
|
||||
Exists --> |否| NotFound["返回 404"]
|
||||
Exists --> |是| Apply["应用变更字段"]
|
||||
Apply --> Flush["flush/refresh"]
|
||||
Flush --> UEnd(["结束"])
|
||||
DStart(["删除入口"]) --> DGet["根据 id 查询科室"]
|
||||
DGet --> DExists{"是否存在?"}
|
||||
DExists --> |否| DNotFound["返回 404"]
|
||||
DExists --> |是| CheckChildren["检查是否存在子节点"]
|
||||
CheckChildren --> HasChild{"有子节点?"}
|
||||
HasChild --> |是| Block["返回错误(不可删除)"]
|
||||
HasChild --> |否| Delete["删除并返回成功"]
|
||||
Delete --> DEnd(["结束"])
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L80-L110)
|
||||
|
||||
章节来源
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L80-L110)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L83-L107)
|
||||
|
||||
### 前端集成与使用示例
|
||||
- 列表页面:支持按关键字(名称/编码)、类型筛选,分页展示
|
||||
- 树形选择:上级科室使用树形选择器,便于层级配置
|
||||
- 新增/编辑:表单校验必填字段,提交后刷新列表与树
|
||||
- 删除:二次确认,防止误删
|
||||
|
||||
章节来源
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L103-L272)
|
||||
- [department.js](file://frontend/src/api/department.js#L1-L32)
|
||||
|
||||
## 依赖关系分析
|
||||
- 模型层依赖数据库引擎与枚举类型,定义了 Department 的结构与约束
|
||||
- 服务层依赖模型层,提供业务逻辑与数据处理
|
||||
- API 层依赖服务层与安全中间件,提供对外接口
|
||||
- 前端依赖 API 封装,调用后端接口完成用户交互
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
FE["前端 Views/API"] --> API["FastAPI 路由"]
|
||||
API --> SVC["Service 业务层"]
|
||||
SVC --> MODEL["ORM 模型层"]
|
||||
MODEL --> DB["数据库"]
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L13-L149)
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L1-L108)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L103-L272)
|
||||
- [department.js](file://frontend/src/api/department.js#L1-L32)
|
||||
|
||||
## 性能考量
|
||||
- 查询优化
|
||||
- 列表与树形查询均按 sort_order 与 id 排序,保证稳定顺序
|
||||
- 服务层一次性加载所有科室,避免 N+1 查询
|
||||
- 索引策略
|
||||
- 按类型与父节点建立索引,提升过滤与层级查询效率
|
||||
- 缓存建议
|
||||
- 树形结构可考虑缓存热点数据,减少重复构建
|
||||
- 分页与并发
|
||||
- 列表查询支持分页,避免一次性加载过多数据
|
||||
- 删除前检查子节点,避免事务回滚与锁竞争
|
||||
|
||||
## 故障排除指南
|
||||
- 创建失败:编码重复
|
||||
- 现象:创建接口返回错误
|
||||
- 处理:检查是否存在相同编码,修改后重试
|
||||
- 删除失败:存在子节点
|
||||
- 现象:删除接口返回错误
|
||||
- 处理:先删除子节点或调整层级后再删除
|
||||
- 树形不正确:层级或排序异常
|
||||
- 现象:树形选择器显示层级混乱
|
||||
- 处理:检查 parent_id 与 sort_order 设置,重新保存
|
||||
- 前端显示异常:类型标签或状态开关无效
|
||||
- 现象:类型标签颜色/文案不一致,状态切换无效
|
||||
- 处理:确认枚举值与前端映射一致,检查事件绑定
|
||||
|
||||
章节来源
|
||||
- [departments.py](file://backend/app/api/v1/departments.py#L74-L77)
|
||||
- [department_service.py](file://backend/app/services/department_service.py#L102-L107)
|
||||
- [Departments.vue](file://frontend/src/views/basic/Departments.vue#L143-L161)
|
||||
|
||||
## 结论
|
||||
Department 模型通过清晰的字段设计、严格的约束与完善的层级计算,为医院绩效系统的组织管理提供了可靠的数据基础。结合 DeptType 的分类与树形结构,能够灵活支撑各类科室的差异化需求,并通过前后端协同实现高效、稳定的科室信息管理。
|
||||
|
||||
## 附录
|
||||
|
||||
### 字段与约束对照表
|
||||
- 字段名:name
|
||||
- 类型:字符串
|
||||
- 约束:必填,长度 ≤ 100
|
||||
- 用途:显示与检索
|
||||
- 字段名:code
|
||||
- 类型:字符串
|
||||
- 约束:必填,唯一,长度 ≤ 20
|
||||
- 用途:业务识别与去重
|
||||
- 字段名:dept_type
|
||||
- 类型:枚举
|
||||
- 约束:必填
|
||||
- 用途:类型分类与模板匹配
|
||||
- 字段名:parent_id
|
||||
- 类型:整型
|
||||
- 约束:可空,外键指向自身 id
|
||||
- 用途:树形层级
|
||||
- 字段名:level
|
||||
- 类型:整型
|
||||
- 约束:默认 1,创建时根据父级 +1
|
||||
- 用途:层级深度
|
||||
- 字段名:sort_order
|
||||
- 类型:整型
|
||||
- 约束:默认 0
|
||||
- 用途:排序与展示顺序
|
||||
- 字段名:is_active
|
||||
- 类型:布尔
|
||||
- 约束:默认启用
|
||||
- 用途:启用/停用控制
|
||||
- 字段名:description
|
||||
- 类型:文本
|
||||
- 约束:可空
|
||||
- 用途:补充说明
|
||||
- 字段名:created_at/updated_at
|
||||
- 类型:时间戳
|
||||
- 约束:自动维护
|
||||
- 用途:审计与追踪
|
||||
|
||||
章节来源
|
||||
- [models.py](file://backend/app/models/models.py#L66-L76)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L64-L72)
|
||||
452
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/系统基础模型.md
Normal file
452
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/系统基础模型.md
Normal file
@@ -0,0 +1,452 @@
|
||||
# 系统基础模型
|
||||
|
||||
<cite>
|
||||
**本文引用的文件**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py)
|
||||
- [backend/app/api/v1/menus.py](file://backend/app/api/v1/menus.py)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py)
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py)
|
||||
- [backend/app/core/config.py](file://backend/app/core/config.py)
|
||||
- [backend/app/main.py](file://backend/app/main.py)
|
||||
- [docs/详细设计.md](file://docs/详细设计.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构总览](#架构总览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排查指南](#故障排查指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
本文件聚焦系统基础模型,围绕以下核心实体展开:用户(User)、菜单(Menu)、指标模板(IndicatorTemplate)、模板指标(TemplateIndicator)。文档将深入解释这些模型的设计理念、实现细节与相互关系,涵盖用户认证与授权、菜单权限管理、指标模板系统、模板与指标的关联关系、用户角色管理、菜单层级结构、模板类型分类、模板指标权重与排序机制、用户与员工的关联关系、菜单父子层级、模板激活状态管理等主题。同时提供系统配置示例、权限控制机制与模板管理最佳实践。
|
||||
|
||||
## 项目结构
|
||||
后端采用 FastAPI + SQLAlchemy 2.0 异步 ORM 的分层架构:
|
||||
- models 层:定义数据库模型与枚举类型
|
||||
- schemas 层:定义 Pydantic 数据模式(输入/输出)
|
||||
- api 层:定义路由与权限依赖
|
||||
- services 层:封装业务逻辑
|
||||
- core 层:安全、配置、数据库连接等基础设施
|
||||
- main:应用入口与中间件注册
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "应用层"
|
||||
API_AUTH["API: /api/v1/auth"]
|
||||
API_MENUS["API: /api/v1/menus"]
|
||||
API_TEMPLATES["API: /api/v1/templates"]
|
||||
end
|
||||
subgraph "服务层"
|
||||
S_AUTH["Security 模块"]
|
||||
S_MENU["MenuService"]
|
||||
S_TEMPLATE["TemplateService"]
|
||||
end
|
||||
subgraph "模型层"
|
||||
M_USER["User"]
|
||||
M_MENU["Menu"]
|
||||
M_INDICATOR["Indicator"]
|
||||
M_TEMPLATE["IndicatorTemplate"]
|
||||
M_TINDICATOR["TemplateIndicator"]
|
||||
end
|
||||
API_AUTH --> S_AUTH
|
||||
API_MENUS --> S_MENU
|
||||
API_TEMPLATES --> S_TEMPLATE
|
||||
S_AUTH --> M_USER
|
||||
S_MENU --> M_MENU
|
||||
S_TEMPLATE --> M_TEMPLATE
|
||||
S_TEMPLATE --> M_TINDICATOR
|
||||
S_TEMPLATE --> M_INDICATOR
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L1-L74)
|
||||
- [backend/app/api/v1/menus.py](file://backend/app/api/v1/menus.py#L1-L164)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L1-L272)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L1-L137)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L1-L293)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L244-L438)
|
||||
|
||||
章节来源
|
||||
- [backend/app/main.py](file://backend/app/main.py#L1-L92)
|
||||
- [backend/app/core/config.py](file://backend/app/core/config.py#L1-L47)
|
||||
|
||||
## 核心组件
|
||||
本节对 User、Menu、IndicatorTemplate、TemplateIndicator 四个核心模型进行系统性解析,包括字段含义、约束、关系与索引策略。
|
||||
|
||||
- User(系统用户)
|
||||
- 关键点:用户名唯一、密码哈希存储、关联员工(可选)、角色(字符串)、启用状态、最后登录时间
|
||||
- 关系:与 Staff 为一对一(外键关联)
|
||||
- 权限:通过角色字段区分 admin/manager/staff;安全中间件提供获取当前用户、激活用户、管理员/经理权限校验
|
||||
- Menu(系统菜单)
|
||||
- 关键点:父子自引用(parent_id → menus.id)、菜单类型(菜单/按钮)、排序、可见性、启用状态
|
||||
- 关系:自关联 parent/children;支持树形结构查询
|
||||
- 权限:菜单权限标识(permission)用于前端路由鉴权
|
||||
- IndicatorTemplate(指标模板)
|
||||
- 关键点:模板类型(TemplateType)、维度权重(JSON 字符串)、考核周期、启用状态
|
||||
- 关系:一对多到 TemplateIndicator
|
||||
- TemplateIndicator(模板指标)
|
||||
- 关键点:与 Indicator 多对一、分类(category)、目标值/单位、权重、评分方法/参数、排序、备注
|
||||
- 关系:与 Indicator 一对一(反向为多对一)
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L244-L438)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L313-L346)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L582-L639)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L698-L743)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L654-L696)
|
||||
|
||||
## 架构总览
|
||||
系统采用前后端分离,后端提供 REST API,前端通过权限标识与菜单树渲染导航。认证采用 JWT,菜单树仅返回可见且启用项,模板管理支持按类型与启用状态筛选。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant FE as "前端"
|
||||
participant API as "API 路由"
|
||||
participant SEC as "安全模块"
|
||||
participant SVC as "服务层"
|
||||
participant DB as "数据库"
|
||||
FE->>API : 登录请求
|
||||
API->>SEC : 校验用户名/密码
|
||||
SEC->>DB : 查询用户
|
||||
DB-->>SEC : 用户记录
|
||||
SEC-->>API : 生成访问令牌
|
||||
API-->>FE : 返回令牌
|
||||
FE->>API : 获取菜单树
|
||||
API->>SEC : 获取当前激活用户
|
||||
SEC-->>API : 当前用户
|
||||
API->>SVC : 查询菜单树
|
||||
SVC->>DB : 查询根菜单可见且启用
|
||||
DB-->>SVC : 菜单集合
|
||||
SVC-->>API : 菜单树
|
||||
API-->>FE : 返回菜单树
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L17-L38)
|
||||
- [backend/app/api/v1/menus.py](file://backend/app/api/v1/menus.py#L17-L29)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L16-L29)
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py#L55-L91)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 用户与认证授权
|
||||
- 认证流程
|
||||
- 登录:OAuth2Password 请求表单,校验密码哈希,检查用户启用状态,签发访问令牌
|
||||
- 注册:检查用户名唯一性,生成密码哈希,创建用户记录
|
||||
- 当前用户:从 JWT 提取用户 ID,查询用户并校验启用状态
|
||||
- 权限:管理员(admin)与经理(manager)具备更高操作权限
|
||||
- 角色与权限
|
||||
- User.role 控制资源访问范围
|
||||
- 路由层通过依赖注入校验当前用户角色与状态
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as "客户端"
|
||||
participant AuthAPI as "Auth API"
|
||||
participant Security as "Security"
|
||||
participant DB as "数据库"
|
||||
Client->>AuthAPI : POST /api/v1/auth/login
|
||||
AuthAPI->>DB : 查询用户
|
||||
DB-->>AuthAPI : 用户(含密码哈希)
|
||||
AuthAPI->>Security : 验证密码
|
||||
Security-->>AuthAPI : 校验结果
|
||||
AuthAPI->>Security : 生成访问令牌
|
||||
AuthAPI-->>Client : {access_token, token_type}
|
||||
Client->>AuthAPI : GET /api/v1/auth/me
|
||||
AuthAPI->>Security : 获取当前激活用户
|
||||
Security->>DB : 查询用户
|
||||
DB-->>Security : 用户
|
||||
Security-->>AuthAPI : 当前用户
|
||||
AuthAPI-->>Client : 用户信息
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L17-L74)
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py#L24-L91)
|
||||
|
||||
章节来源
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L1-L74)
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py#L1-L110)
|
||||
|
||||
### 菜单与权限管理
|
||||
- 菜单模型
|
||||
- 支持菜单/按钮两类,父子自引用,排序与可见性控制
|
||||
- 菜单树查询:仅返回顶层、可见且启用的菜单,并递归加载子节点
|
||||
- 权限控制
|
||||
- 菜单权限标识(permission)用于前端路由鉴权
|
||||
- 菜单管理 API 通过角色依赖限制创建/更新/删除操作
|
||||
- 初始化
|
||||
- 支持初始化默认菜单,避免重复初始化
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start(["获取菜单树"]) --> BuildQuery["构建查询: 顶层菜单<br/>可见且启用"]
|
||||
BuildQuery --> LoadChildren["加载子节点关系"]
|
||||
LoadChildren --> OrderBy["按排序与ID排序"]
|
||||
OrderBy --> ToDict["_menu_to_dict 递归转字典"]
|
||||
ToDict --> End(["返回菜单树"])
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L16-L29)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L101-L109)
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L347-L373)
|
||||
- [backend/app/api/v1/menus.py](file://backend/app/api/v1/menus.py#L1-L164)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L1-L137)
|
||||
|
||||
### 指标模板系统
|
||||
- 模板类型
|
||||
- 通用模板、手术临床、非手术有病房、非手术无病房、医技、护理、行政、后勤
|
||||
- 维度权重
|
||||
- 模板可配置 BSC 四维度权重(JSON 字符串),用于汇总计算
|
||||
- 考核周期
|
||||
- 支持月度/年度等周期配置
|
||||
- 列表与详情
|
||||
- 支持按类型与启用状态筛选,返回模板指标数量
|
||||
- 详情包含模板基本信息与完整指标列表(含指标名称、编码、类型、维度、权重、排序等)
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class IndicatorTemplate {
|
||||
+template_name
|
||||
+template_code
|
||||
+template_type
|
||||
+dimension_weights
|
||||
+assessment_cycle
|
||||
+is_active
|
||||
+indicators[]
|
||||
}
|
||||
class TemplateIndicator {
|
||||
+indicator_id
|
||||
+category
|
||||
+target_value
|
||||
+target_unit
|
||||
+weight
|
||||
+scoring_method
|
||||
+scoring_params
|
||||
+sort_order
|
||||
+remark
|
||||
+indicator
|
||||
}
|
||||
class Indicator {
|
||||
+name
|
||||
+code
|
||||
+indicator_type
|
||||
+bs_dimension
|
||||
+weight
|
||||
+max_score
|
||||
}
|
||||
IndicatorTemplate "1" --> "many" TemplateIndicator : "包含"
|
||||
TemplateIndicator "many" --> "1" Indicator : "关联"
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L387-L438)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L698-L743)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L654-L696)
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L375-L438)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L640-L743)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L1-L272)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L1-L293)
|
||||
|
||||
### 模板与指标的关联关系
|
||||
- 关联表 TemplateIndicator
|
||||
- 唯一约束:同一模板下指标唯一
|
||||
- 排序字段 sort_order 决定展示顺序
|
||||
- 支持批量添加,自动补齐排序
|
||||
- 权重与排序机制
|
||||
- 模板层与指标层均支持权重配置
|
||||
- 汇总时需遵循维度权重与指标权重的乘积规则(由上层业务逻辑决定)
|
||||
- 激活状态管理
|
||||
- 模板与指标均可启用/停用,影响使用范围与计算
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L411-L438)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L160-L207)
|
||||
|
||||
### 用户与员工的关联关系
|
||||
- User 与 Staff
|
||||
- User.staff_id 外键关联 Staff.id,表示系统用户与员工的绑定关系
|
||||
- 便于登录后获取员工信息与权限边界
|
||||
- 员工状态与部门
|
||||
- Staff.status 与 Department.parent_id/level 等字段共同构成组织与人员管理基础
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L114)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L244-L261)
|
||||
|
||||
### 菜单层级结构
|
||||
- 自引用关系
|
||||
- Menu.parent_id → Menu.id,支持任意层级
|
||||
- 服务层通过 selectinload 预加载 children,避免 N+1 查询
|
||||
- 树形渲染
|
||||
- 顶层查询(parent_id IS NULL),按 sort_order 与 id 排序
|
||||
- 递归转换为字典树,供前端渲染
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L347-L373)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L16-L29)
|
||||
|
||||
### 模板类型分类逻辑
|
||||
- TemplateType 枚举覆盖全院主要科室类型,便于按类型匹配模板
|
||||
- 服务层提供类型标签映射,便于前端展示
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L375-L385)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L270-L283)
|
||||
|
||||
### 权重与排序机制
|
||||
- 指标层权重
|
||||
- Indicator.weight 与 TemplateIndicator.weight 双层权重
|
||||
- 数据库层对指标权重设置正数约束
|
||||
- 排序
|
||||
- TemplateIndicator.sort_order 决定模板内指标顺序
|
||||
- 批量添加时可按传入顺序补齐排序
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L124-L146)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L421-L427)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L256-L267)
|
||||
|
||||
### 激活状态管理
|
||||
- 模板与菜单均提供 is_active 字段
|
||||
- 菜单树查询默认仅返回启用项
|
||||
- 模板列表支持按 is_active 过滤
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L398-L398)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L360-L360)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L16-L21)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L22-L42)
|
||||
|
||||
## 依赖分析
|
||||
- 模型依赖
|
||||
- User ←→ Staff(一对一外键)
|
||||
- Menu ←→ Menu(自引用)
|
||||
- IndicatorTemplate → TemplateIndicator → Indicator(多对一)
|
||||
- 服务依赖
|
||||
- MenuService 依赖 Menu 模型
|
||||
- TemplateService 依赖 IndicatorTemplate、TemplateIndicator、Indicator 模型
|
||||
- API 依赖
|
||||
- auth 路由依赖 Security 与 User 模型
|
||||
- menus 路由依赖 MenuService 与 Menu 模型
|
||||
- templates 路由依赖 TemplateService 与模板相关 Schema
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
A["User"] <- --> B["Staff"]
|
||||
C["Menu"] --自引用 --> C
|
||||
D["IndicatorTemplate"] --> E["TemplateIndicator"]
|
||||
E --> F["Indicator"]
|
||||
G["MenuService"] --> C
|
||||
H["TemplateService"] --> D
|
||||
H --> E
|
||||
H --> F
|
||||
I["Auth API"] --> G
|
||||
J["Menus API"] --> G
|
||||
K["Templates API"] --> H
|
||||
```
|
||||
|
||||
图表来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L438)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L1-L137)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L1-L293)
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L1-L74)
|
||||
- [backend/app/api/v1/menus.py](file://backend/app/api/v1/menus.py#L1-L164)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L1-L272)
|
||||
|
||||
## 性能考虑
|
||||
- 查询优化
|
||||
- 使用 selectinload 预加载关系,减少 N+1 查询
|
||||
- 菜单树查询限定顶层、可见与启用条件
|
||||
- 索引策略
|
||||
- 模型层为常用过滤字段建立索引(如模板类型、菜单可见性、指标权重约束)
|
||||
- 分页与排序
|
||||
- 模板列表支持分页与排序,避免一次性加载过多数据
|
||||
- 缓存与并发
|
||||
- 配置层提供数据库连接池参数,建议在生产环境按负载调优
|
||||
|
||||
章节来源
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L82-L85)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L368-L372)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L143-L146)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L16-L29)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L22-L42)
|
||||
- [backend/app/core/config.py](file://backend/app/core/config.py#L18-L22)
|
||||
|
||||
## 故障排查指南
|
||||
- 登录失败
|
||||
- 检查用户名是否存在、密码是否正确、用户是否启用
|
||||
- 查看安全模块的凭据验证与令牌生成流程
|
||||
- 菜单不可见
|
||||
- 确认菜单 is_visible 与 is_active 状态
|
||||
- 检查菜单树查询是否仅返回可见启用项
|
||||
- 模板操作失败
|
||||
- 检查模板编码唯一性、模板与指标是否存在、唯一约束冲突
|
||||
- 确认排序字段是否正确传递
|
||||
- 权限不足
|
||||
- 确认当前用户角色(admin/manager/staff)
|
||||
- 检查路由依赖是否正确应用
|
||||
|
||||
章节来源
|
||||
- [backend/app/api/v1/auth.py](file://backend/app/api/v1/auth.py#L17-L38)
|
||||
- [backend/app/services/menu_service.py](file://backend/app/services/menu_service.py#L86-L98)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L136-L140)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L167-L182)
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py#L94-L109)
|
||||
|
||||
## 结论
|
||||
本系统基础模型围绕 User、Menu、IndicatorTemplate、TemplateIndicator 构建,通过清晰的枚举与约束、合理的索引与查询策略、严格的权限控制与安全中间件,实现了用户认证授权、菜单权限管理、指标模板体系与模板-指标关联的完整闭环。模板类型覆盖全院主要科室,权重与排序机制满足多维度汇总需求,激活状态管理确保系统灵活性。配合服务层与 API 层的职责分离,系统具备良好的扩展性与可维护性。
|
||||
|
||||
## 附录
|
||||
|
||||
### 系统配置示例
|
||||
- JWT 配置
|
||||
- SECRET_KEY、ALGORITHM、ACCESS_TOKEN_EXPIRE_MINUTES
|
||||
- 数据库连接
|
||||
- DATABASE_URL、DATABASE_POOL_SIZE、DATABASE_MAX_OVERFLOW
|
||||
- 跨域与分页
|
||||
- CORS_ORIGINS、DEFAULT_PAGE_SIZE、MAX_PAGE_SIZE
|
||||
|
||||
章节来源
|
||||
- [backend/app/core/config.py](file://backend/app/core/config.py#L9-L47)
|
||||
|
||||
### 权限控制机制
|
||||
- 当前用户获取与校验
|
||||
- 从 JWT 解析用户 ID,查询用户并校验启用状态
|
||||
- 角色权限
|
||||
- 管理员(admin):最高权限
|
||||
- 经理(manager):部分管理操作
|
||||
- 普通员工(staff):受限操作
|
||||
|
||||
章节来源
|
||||
- [backend/app/core/security.py](file://backend/app/core/security.py#L55-L109)
|
||||
|
||||
### 模板管理最佳实践
|
||||
- 模板类型选择
|
||||
- 根据科室类型选择对应模板,避免跨类型混用
|
||||
- 维度权重设计
|
||||
- 明确财务/客户/内部流程/学习与成长的权重范围与合计
|
||||
- 指标权重与排序
|
||||
- 指标层权重与模板层权重协同,排序字段保持连续与稳定
|
||||
- 激活状态
|
||||
- 新建模板先启用少量指标进行测试,逐步放开
|
||||
|
||||
章节来源
|
||||
- [docs/详细设计.md](file://docs/详细设计.md#L69-L95)
|
||||
- [backend/app/api/v1/templates.py](file://backend/app/api/v1/templates.py#L63-L74)
|
||||
- [backend/app/services/template_service.py](file://backend/app/services/template_service.py#L270-L283)
|
||||
587
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/绩效计划模型.md
Normal file
587
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/绩效计划模型.md
Normal file
@@ -0,0 +1,587 @@
|
||||
# 绩效计划模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
- [performance_plan.js](file://frontend/src/api/performance_plan.js)
|
||||
- [create_plan_tables.py](file://backend/create_plan_tables.py)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
本文件详细阐述了医院绩效系统的绩效计划模型设计与实现。该模型支持多层级、多维度的绩效管理需求,涵盖从医院级到个人级的完整计划体系,提供完善的审批流程、版本控制和执行跟踪功能。系统采用现代化的前后端分离架构,后端基于FastAPI和SQLAlchemy,前端使用Vue.js框架。
|
||||
|
||||
## 项目结构
|
||||
|
||||
绩效计划模型位于后端应用的核心模块中,采用清晰的分层架构设计:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "后端架构"
|
||||
API[API层<br/>performance_plans.py]
|
||||
Service[服务层<br/>performance_plan_service.py]
|
||||
Model[模型层<br/>models.py]
|
||||
Schema[数据模式<br/>schemas.py]
|
||||
DB[(数据库)]
|
||||
end
|
||||
subgraph "前端架构"
|
||||
Frontend[前端应用<br/>Vue.js]
|
||||
APIClient[API客户端<br/>performance_plan.js]
|
||||
end
|
||||
Frontend --> APIClient
|
||||
APIClient --> API
|
||||
API --> Service
|
||||
Service --> Model
|
||||
Model --> DB
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py#L1-L310)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L1-L342)
|
||||
- [models.py](file://backend/app/models/models.py#L270-L342)
|
||||
|
||||
**章节来源**
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py#L1-L310)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L1-L342)
|
||||
- [models.py](file://backend/app/models/models.py#L270-L342)
|
||||
|
||||
## 核心组件
|
||||
|
||||
### 计划层级枚举(PlanLevel)
|
||||
|
||||
系统定义了三个层级的计划结构,支持从宏观到微观的逐级分解:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class PlanLevel {
|
||||
<<enumeration>>
|
||||
+hospital
|
||||
+department
|
||||
+individual
|
||||
}
|
||||
class PerformancePlan {
|
||||
+int id
|
||||
+string plan_name
|
||||
+string plan_code
|
||||
+PlanLevel plan_level
|
||||
+int plan_year
|
||||
+int plan_month
|
||||
+string plan_type
|
||||
+int department_id
|
||||
+int staff_id
|
||||
+int parent_plan_id
|
||||
+string description
|
||||
+string strategic_goals
|
||||
+string key_initiatives
|
||||
+PlanStatus status
|
||||
+int submitter_id
|
||||
+datetime submit_time
|
||||
+int approver_id
|
||||
+datetime approve_time
|
||||
+string approve_remark
|
||||
+int version
|
||||
+bool is_active
|
||||
}
|
||||
PerformancePlan --> PlanLevel : uses
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L263-L268)
|
||||
- [models.py](file://backend/app/models/models.py#L270-L312)
|
||||
|
||||
### 计划状态枚举(PlanStatus)
|
||||
|
||||
状态管理贯穿整个计划生命周期,确保流程的规范性和可追溯性:
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 草稿
|
||||
草稿 --> 待审批 : 提交
|
||||
待审批 --> 已批准 : 审批通过
|
||||
待审批 --> 已驳回 : 审批驳回
|
||||
已批准 --> 执行中 : 激活
|
||||
已批准 --> 已完成 : 结束
|
||||
执行中 --> 已完成 : 结束
|
||||
已完成 --> 取消 : 取消
|
||||
草稿 --> 取消 : 删除
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L233-L242)
|
||||
|
||||
### 时间维度管理
|
||||
|
||||
系统支持年度和月度两种时间维度,满足不同层级的计划管理需求:
|
||||
|
||||
| 时间维度 | 字段 | 用途 | 限制 |
|
||||
|---------|------|------|------|
|
||||
| 年度计划 | plan_year | 计划年度 | 必填 |
|
||||
| 月度计划 | plan_year, plan_month | 计划年度和月份 | 月度计划时必填 |
|
||||
| 计划类型 | plan_type | annual/monthly | 默认年度 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L277-L280)
|
||||
|
||||
## 架构概览
|
||||
|
||||
### 数据模型关系图
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
PERFORMANCE_PLANS {
|
||||
int id PK
|
||||
string plan_name
|
||||
string plan_code UK
|
||||
enum plan_level
|
||||
int plan_year
|
||||
int plan_month
|
||||
string plan_type
|
||||
int department_id FK
|
||||
int staff_id FK
|
||||
int parent_plan_id FK
|
||||
text strategic_goals
|
||||
text key_initiatives
|
||||
enum status
|
||||
int submitter_id FK
|
||||
datetime submit_time
|
||||
int approver_id FK
|
||||
datetime approve_time
|
||||
text approve_remark
|
||||
int version
|
||||
bool is_active
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
PLAN_KPI_RELATIONS {
|
||||
int id PK
|
||||
int plan_id FK
|
||||
int indicator_id FK
|
||||
float target_value
|
||||
string target_unit
|
||||
float weight
|
||||
string scoring_method
|
||||
text scoring_params
|
||||
text remark
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
DEPARTMENTS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
enum dept_type
|
||||
int parent_id FK
|
||||
int level
|
||||
int sort_order
|
||||
bool is_active
|
||||
text description
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
STAFF {
|
||||
int id PK
|
||||
string employee_id UK
|
||||
string name
|
||||
int department_id FK
|
||||
string position
|
||||
string title
|
||||
string phone
|
||||
string email
|
||||
numeric base_salary
|
||||
numeric performance_ratio
|
||||
enum status
|
||||
datetime hire_date
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
USERS {
|
||||
int id PK
|
||||
string username UK
|
||||
string password_hash
|
||||
int staff_id FK
|
||||
string role
|
||||
bool is_active
|
||||
datetime last_login
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
enum indicator_type
|
||||
enum bs_dimension
|
||||
numeric weight
|
||||
numeric max_score
|
||||
numeric target_value
|
||||
string target_unit
|
||||
text calculation_method
|
||||
text assessment_method
|
||||
text deduction_standard
|
||||
string data_source
|
||||
text applicable_dept_types
|
||||
bool is_veto
|
||||
bool is_active
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
PERFORMANCE_PLANS ||--o{ PLAN_KPI_RELATIONS : contains
|
||||
PLAN_KPI_RELATIONS }o--|| INDICATORS : links_to
|
||||
PERFORMANCE_PLANS }o--|| DEPARTMENTS : belongs_to
|
||||
PERFORMANCE_PLANS }o--|| STAFF : responsible_for
|
||||
PERFORMANCE_PLANS }o--|| USERS : submitted_by
|
||||
PERFORMANCE_PLANS }o--|| USERS : approved_by
|
||||
DEPARTMENTS ||--o{ PERFORMANCE_PLANS : hosts
|
||||
STAFF ||--o{ PERFORMANCE_PLANS : creates
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L62-L438)
|
||||
|
||||
### API接口架构
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as 前端客户端
|
||||
participant API as API层
|
||||
participant Service as 服务层
|
||||
participant DB as 数据库
|
||||
Client->>API : GET /plans
|
||||
API->>Service : get_list()
|
||||
Service->>DB : 查询计划列表
|
||||
DB-->>Service : 返回结果集
|
||||
Service-->>API : 计划列表
|
||||
API-->>Client : JSON响应
|
||||
Client->>API : POST /plans
|
||||
API->>Service : create()
|
||||
Service->>DB : 插入新计划
|
||||
DB-->>Service : 返回新ID
|
||||
Service-->>API : 完整计划对象
|
||||
API-->>Client : 创建成功
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py#L21-L66)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L76-L102)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L270-L342)
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py#L1-L310)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L1-L342)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### PerformancePlan模型详解
|
||||
|
||||
PerformancePlan是整个绩效计划系统的核心实体,承载着完整的计划信息和业务逻辑:
|
||||
|
||||
#### 核心属性设计
|
||||
|
||||
| 属性名 | 类型 | 必填 | 描述 | 约束 |
|
||||
|--------|------|------|------|------|
|
||||
| plan_name | string | 是 | 计划名称 | 最大长度200 |
|
||||
| plan_code | string | 是 | 计划编码 | 唯一约束,最大长度50 |
|
||||
| plan_level | PlanLevel | 是 | 计划层级 | 枚举值:hospital/department/individual |
|
||||
| plan_year | int | 是 | 计划年度 | 必填 |
|
||||
| plan_month | int | 否 | 计划月份 | 月度计划时必填 |
|
||||
| plan_type | string | 否 | 计划类型 | 默认annual,可选monthly |
|
||||
| department_id | int | 否 | 所属科室ID | 外键约束 |
|
||||
| staff_id | int | 否 | 责任人ID | 外键约束 |
|
||||
| parent_plan_id | int | 否 | 上级计划ID | 自引用外键 |
|
||||
| strategic_goals | text | 否 | 战略目标 | 文本内容 |
|
||||
| key_initiatives | text | 否 | 关键举措 | 文本内容 |
|
||||
| version | int | 否 | 版本号 | 默认1,自增 |
|
||||
| is_active | bool | 否 | 是否启用 | 默认true |
|
||||
|
||||
#### 关系映射
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class PerformancePlan {
|
||||
+Department department
|
||||
+Staff staff
|
||||
+PerformancePlan parent_plan
|
||||
+PlanKpiRelation[] kpi_relations
|
||||
+User submitter
|
||||
+User approver
|
||||
+PerformancePlan[] child_plans
|
||||
}
|
||||
class PlanKpiRelation {
|
||||
+PerformancePlan plan
|
||||
+Indicator indicator
|
||||
}
|
||||
class Department {
|
||||
+PerformancePlan[] performance_plans
|
||||
}
|
||||
class Staff {
|
||||
+PerformancePlan[] performance_plans
|
||||
}
|
||||
PerformancePlan --> Department : belongs_to
|
||||
PerformancePlan --> Staff : responsible_for
|
||||
PerformancePlan --> PlanKpiRelation : contains
|
||||
PlanKpiRelation --> Indicator : links_to
|
||||
PerformancePlan --> PerformancePlan : parent_child
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L298-L304)
|
||||
- [models.py](file://backend/app/models/models.py#L314-L338)
|
||||
|
||||
### 计划层级业务含义
|
||||
|
||||
#### 医院级计划(Hospital)
|
||||
- **覆盖范围**:整个医院层面的战略规划
|
||||
- **制定主体**:医院管理层
|
||||
- **关注重点**:医院整体发展战略、资源配置、重大决策
|
||||
- **典型内容**:医院发展规划、重大投资计划、体制改革方案
|
||||
|
||||
#### 科室级计划(Department)
|
||||
- **覆盖范围**:特定临床或医技科室
|
||||
- **制定主体**:科室负责人
|
||||
- **关注重点**:科室业务发展、质量改进、效率提升
|
||||
- **典型内容**:学科建设、人才培养、技术创新
|
||||
|
||||
#### 个人级计划(Individual)
|
||||
- **覆盖范围**:具体员工个人
|
||||
- **制定主体**:员工本人或直接上级
|
||||
- **关注重点**:个人能力发展、工作目标达成
|
||||
- **典型内容**:技能培训、绩效目标、职业发展规划
|
||||
|
||||
### 多级审批流程
|
||||
|
||||
系统实现了严格的多级审批机制,确保计划的合规性和权威性:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> Create["创建草稿计划"]
|
||||
Create --> Submit["提交审批"]
|
||||
Submit --> Review{"审批状态"}
|
||||
Review --> |通过| Approve["审批通过"]
|
||||
Review --> |驳回| Reject["审批驳回"]
|
||||
Approve --> Activate["激活执行"]
|
||||
Reject --> Edit["修改后重新提交"]
|
||||
Activate --> Execute["执行中"]
|
||||
Execute --> Complete["完成"]
|
||||
Edit --> Submit
|
||||
Complete --> Cancel["取消"]
|
||||
Cancel --> End([结束])
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L131-L182)
|
||||
|
||||
### 计划与指标关联关系
|
||||
|
||||
PlanKpiRelation表建立了计划与指标之间的多对多关联:
|
||||
|
||||
#### 关联属性设计
|
||||
|
||||
| 属性名 | 类型 | 必填 | 描述 | 约束 |
|
||||
|--------|------|------|------|------|
|
||||
| target_value | float | 否 | 目标值 | 数值类型 |
|
||||
| target_unit | string | 否 | 目标值单位 | 最大长度50 |
|
||||
| weight | float | 否 | 权重 | 默认1.0 |
|
||||
| scoring_method | string | 否 | 评分方法 | 最大长度50 |
|
||||
| scoring_params | text | 否 | 评分参数 | JSON格式 |
|
||||
| remark | text | 否 | 备注 | 文本内容 |
|
||||
|
||||
#### 关联规则
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
PERFORMANCE_PLANS ||--o{ PLAN_KPI_RELATIONS : contains
|
||||
PLAN_KPI_RELATIONS }o--|| INDICATORS : links_to
|
||||
PLAN_KPI_RELATIONS {
|
||||
unique(plan_id, indicator_id)
|
||||
}
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L314-L338)
|
||||
|
||||
### 版本控制机制
|
||||
|
||||
系统内置版本控制功能,支持计划的迭代更新:
|
||||
|
||||
#### 版本管理策略
|
||||
|
||||
1. **初始版本**:新建计划时自动设置为1
|
||||
2. **版本递增**:每次更新操作时版本号+1
|
||||
3. **历史追踪**:通过版本号区分不同版本的计划
|
||||
4. **冲突处理**:并发更新时通过版本号避免数据覆盖
|
||||
|
||||
#### 版本控制API
|
||||
|
||||
| 接口 | 方法 | 功能 | 权限要求 |
|
||||
|------|------|------|----------|
|
||||
| /plans | POST | 创建新计划 | 普通用户 |
|
||||
| /plans/{id} | PUT | 更新计划 | 管理员/经理 |
|
||||
| /plans/{id}/submit | POST | 提交审批 | 普通用户 |
|
||||
| /plans/{id}/approve | POST | 审批计划 | 管理员/经理 |
|
||||
| /plans/{id}/activate | POST | 激活计划 | 管理员/经理 |
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L293)
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L105-L128)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
### 数据库依赖关系
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
subgraph "核心表"
|
||||
PP[performance_plans]
|
||||
PKR[plan_kpi_relations]
|
||||
IND[indicators]
|
||||
DEPT[departments]
|
||||
STAFF[staff]
|
||||
USR[users]
|
||||
end
|
||||
PP --> DEPT
|
||||
PP --> STAFF
|
||||
PP --> USR
|
||||
PP --> PP
|
||||
PKR --> PP
|
||||
PKR --> IND
|
||||
DEPT --> DEPT
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L22-L183)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L21-L96)
|
||||
|
||||
### 前后端交互依赖
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant FE as 前端
|
||||
participant API as 后端API
|
||||
participant SVC as 服务层
|
||||
participant DB as 数据库
|
||||
FE->>API : 发起HTTP请求
|
||||
API->>SVC : 调用业务逻辑
|
||||
SVC->>DB : 执行数据库操作
|
||||
DB-->>SVC : 返回查询结果
|
||||
SVC-->>API : 返回业务数据
|
||||
API-->>FE : 返回JSON响应
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [performance_plan.js](file://frontend/src/api/performance_plan.js#L1-L67)
|
||||
|
||||
### 外部依赖
|
||||
|
||||
- **FastAPI**:Web框架和API开发
|
||||
- **SQLAlchemy**:ORM框架和数据库抽象
|
||||
- **Alembic**:数据库迁移工具
|
||||
- **Vue.js**:前端框架
|
||||
- **PostgreSQL**:数据库引擎
|
||||
|
||||
**章节来源**
|
||||
- [performance_plan.js](file://frontend/src/api/performance_plan.js#L1-L67)
|
||||
- [create_plan_tables.py](file://backend/create_plan_tables.py#L1-L19)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 数据库性能优化
|
||||
|
||||
1. **索引策略**
|
||||
- 计划层级索引:`idx_plan_level`
|
||||
- 计划年度索引:`idx_plan_year`
|
||||
- 状态索引:`idx_plan_status`
|
||||
- 部门索引:`idx_plan_department`
|
||||
|
||||
2. **查询优化**
|
||||
- 使用`selectinload`进行关联查询
|
||||
- 实现分页查询避免大数据量加载
|
||||
- 缓存常用查询结果
|
||||
|
||||
3. **连接池管理**
|
||||
- 异步数据库连接
|
||||
- 连接池大小合理配置
|
||||
- 连接超时和重试机制
|
||||
|
||||
### 前端性能优化
|
||||
|
||||
1. **API调用优化**
|
||||
- 批量数据请求
|
||||
- 请求去重和缓存
|
||||
- 错误重试机制
|
||||
|
||||
2. **界面渲染优化**
|
||||
- 组件懒加载
|
||||
- 虚拟滚动处理大量数据
|
||||
- 图表组件按需渲染
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题及解决方案
|
||||
|
||||
#### 计划创建失败
|
||||
**问题**:创建计划时报错
|
||||
**可能原因**:
|
||||
- 计划编码重复
|
||||
- 必填字段缺失
|
||||
- 外键约束错误
|
||||
|
||||
**解决步骤**:
|
||||
1. 检查计划编码是否唯一
|
||||
2. 验证所有必填字段
|
||||
3. 确认关联实体存在
|
||||
|
||||
#### 审批流程异常
|
||||
**问题**:审批状态无法正常流转
|
||||
**可能原因**:
|
||||
- 当前状态不正确
|
||||
- 权限不足
|
||||
- 数据库事务未提交
|
||||
|
||||
**解决步骤**:
|
||||
1. 检查当前计划状态
|
||||
2. 验证用户权限
|
||||
3. 查看数据库事务日志
|
||||
|
||||
#### 性能问题
|
||||
**问题**:查询响应缓慢
|
||||
**可能原因**:
|
||||
- 缺少必要索引
|
||||
- 查询条件不当
|
||||
- 数据量过大
|
||||
|
||||
**解决步骤**:
|
||||
1. 添加缺失索引
|
||||
2. 优化查询条件
|
||||
3. 实施分页查询
|
||||
|
||||
**章节来源**
|
||||
- [performance_plan_service.py](file://backend/app/services/performance_plan_service.py#L131-L182)
|
||||
- [performance_plans.py](file://backend/app/api/v1/performance_plans.py#L194-L225)
|
||||
|
||||
## 结论
|
||||
|
||||
绩效计划模型通过精心设计的数据结构和严谨的业务流程,为医院提供了完整的绩效管理体系。系统的主要优势包括:
|
||||
|
||||
1. **层次化设计**:支持从医院级到个人级的多层级计划管理
|
||||
2. **流程规范化**:完善的审批流程确保计划的合规性
|
||||
3. **扩展性强**:灵活的指标关联机制支持个性化配置
|
||||
4. **版本控制**:内置版本管理支持计划的迭代演进
|
||||
5. **前后端分离**:现代化的技术栈提供良好的开发体验
|
||||
|
||||
该模型为医院的绩效管理提供了坚实的技术基础,能够有效支撑医院的战略实施和日常运营管理工作。
|
||||
428
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核指标模型.md
Normal file
428
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核指标模型.md
Normal file
@@ -0,0 +1,428 @@
|
||||
# 考核指标模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py)
|
||||
- [init_indicator_templates.py](file://backend/init_indicator_templates.py)
|
||||
- [详细设计文档.md](file://docs/详细设计文档.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
本文件详细阐述了医院绩效系统中的考核指标模型设计与实现。该模型基于平衡计分卡理论,支持财务、客户、内部流程、学习与成长四个维度,涵盖质量、数量、效率、服务、成本等多种指标类型。系统通过明确的权重管理、评分规则和数据源管理,实现了科学、规范的绩效考核体系。
|
||||
|
||||
## 项目结构
|
||||
|
||||
后端采用分层架构设计,主要包含以下层次:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "表现层"
|
||||
API[API路由层]
|
||||
end
|
||||
subgraph "服务层"
|
||||
IndicatorService[指标服务层]
|
||||
AssessmentService[考核服务层]
|
||||
end
|
||||
subgraph "模型层"
|
||||
Indicator[指标模型]
|
||||
Assessment[考核记录模型]
|
||||
AssessmentDetail[考核明细模型]
|
||||
IndicatorTemplate[指标模板模型]
|
||||
TemplateIndicator[模板指标关联模型]
|
||||
end
|
||||
subgraph "数据层"
|
||||
Database[(数据库)]
|
||||
end
|
||||
API --> IndicatorService
|
||||
API --> AssessmentService
|
||||
IndicatorService --> Indicator
|
||||
AssessmentService --> Assessment
|
||||
AssessmentService --> AssessmentDetail
|
||||
Indicator --> AssessmentDetail
|
||||
IndicatorTemplate --> TemplateIndicator
|
||||
Indicator --> Database
|
||||
Assessment --> Database
|
||||
AssessmentDetail --> Database
|
||||
IndicatorTemplate --> Database
|
||||
TemplateIndicator --> Database
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L117-L146)
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py#L1-L142)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
## 核心组件
|
||||
|
||||
### 指标类型枚举 (IndicatorType)
|
||||
|
||||
系统定义了五种核心指标类型,每种类型都有明确的业务含义和适用场景:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class IndicatorType {
|
||||
<<enumeration>>
|
||||
+quality
|
||||
+quantity
|
||||
+efficiency
|
||||
+service
|
||||
+cost
|
||||
}
|
||||
class BSCDimension {
|
||||
<<enumeration>>
|
||||
+financial
|
||||
+customer
|
||||
+internal_process
|
||||
+learning_growth
|
||||
}
|
||||
class Indicator {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+IndicatorType indicator_type
|
||||
+BSCDimension bs_dimension
|
||||
+float weight
|
||||
+float max_score
|
||||
+float target_value
|
||||
+string target_unit
|
||||
+string calculation_method
|
||||
+string assessment_method
|
||||
+string deduction_standard
|
||||
+string data_source
|
||||
+string applicable_dept_types
|
||||
+bool is_veto
|
||||
+bool is_active
|
||||
}
|
||||
Indicator --> IndicatorType : uses
|
||||
Indicator --> BSCDimension : uses
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L54-L61)
|
||||
- [models.py](file://backend/app/models/models.py#L29-L35)
|
||||
- [models.py](file://backend/app/models/models.py#L117-L146)
|
||||
|
||||
### 权重管理机制
|
||||
|
||||
权重是指标体系的核心要素,系统通过以下机制确保权重的合理分配:
|
||||
|
||||
1. **权重范围约束**:权重必须大于0,确保每个指标都有实际意义
|
||||
2. **加权得分计算**:在考核过程中,加权得分 = 指标得分 × 指标权重
|
||||
3. **模板权重继承**:从指标模板中继承权重设置,支持批量配置
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L126-L127)
|
||||
- [models.py](file://backend/app/models/models.py#L144-L145)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L76-L84)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用MVC架构模式,通过清晰的职责分离实现高效的数据处理:
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as 客户端
|
||||
participant API as API路由
|
||||
participant Service as 服务层
|
||||
participant Model as 模型层
|
||||
participant DB as 数据库
|
||||
Client->>API : GET /indicators
|
||||
API->>Service : get_list()
|
||||
Service->>Model : 查询指标列表
|
||||
Model->>DB : 执行SQL查询
|
||||
DB-->>Model : 返回查询结果
|
||||
Model-->>Service : 返回指标对象
|
||||
Service-->>API : 返回指标数据
|
||||
API-->>Client : JSON响应
|
||||
Note over Client,DB : 数据持久化通过ORM映射
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py#L20-L41)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py#L17-L46)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### 指标模型设计
|
||||
|
||||
指标模型是整个系统的核心,包含了完整的考核指标定义:
|
||||
|
||||
#### 核心字段设计
|
||||
|
||||
| 字段名 | 类型 | 描述 | 约束条件 |
|
||||
|--------|------|------|----------|
|
||||
| id | Integer | 主键标识 | 自增 |
|
||||
| name | String | 指标名称 | 非空,最大100字符 |
|
||||
| code | String | 指标编码 | 唯一,非空,最大20字符 |
|
||||
| indicator_type | Enum | 指标类型 | 非空,枚举类型 |
|
||||
| bs_dimension | Enum | BSC维度 | 非空,枚举类型 |
|
||||
| weight | Numeric | 权重 | 默认1.0,>0 |
|
||||
| max_score | Numeric | 最高分值 | 默认100.0 |
|
||||
| target_value | Numeric | 目标值 | 可选 |
|
||||
| target_unit | String | 目标值单位 | 可选,最大50字符 |
|
||||
| calculation_method | Text | 计算方法 | 可选 |
|
||||
| assessment_method | Text | 考核方法 | 可选 |
|
||||
| deduction_standard | Text | 扣分标准 | 可选 |
|
||||
| data_source | String | 数据来源 | 可选,最大100字符 |
|
||||
| applicable_dept_types | Text | 适用科室类型 | JSON数组 |
|
||||
| is_veto | Boolean | 一票否决标志 | 默认False |
|
||||
| is_active | Boolean | 启用状态 | 默认True |
|
||||
|
||||
#### 适用科室类型过滤
|
||||
|
||||
系统通过JSON格式存储适用科室类型,支持灵活的科室匹配:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始筛选]) --> GetDeptTypes["获取指标适用科室类型<br/>JSON数组"]
|
||||
GetDeptTypes --> ParseJSON["解析JSON字符串"]
|
||||
ParseJSON --> CompareDept{"匹配当前科室类型?"}
|
||||
CompareDept --> |是| Include["包含在适用范围内"]
|
||||
CompareDept --> |否| Exclude["排除在适用范围外"]
|
||||
Include --> End([结束])
|
||||
Exclude --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L134)
|
||||
- [indicator_service.py](file://backend/app/services/indicator_service.py#L112-L154)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L121-L138)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L153-L163)
|
||||
|
||||
### 一票否决指标处理
|
||||
|
||||
一票否决是系统的重要风控机制,具有以下特点:
|
||||
|
||||
#### 特殊处理逻辑
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始处理指标]) --> CheckVeto{"是否为一票否决指标?"}
|
||||
CheckVeto --> |否| NormalCalc["正常评分计算"]
|
||||
CheckVeto --> |是| VetoCheck["检查否决条件"]
|
||||
VetoCheck --> VetoTrigger{"否决条件触发?"}
|
||||
VetoTrigger --> |是| ZeroScore["直接得分为0分"]
|
||||
VetoTrigger --> |否| NormalCalc
|
||||
NormalCalc --> End([结束])
|
||||
ZeroScore --> End
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L135)
|
||||
- [init_indicator_templates.py](file://backend/init_indicator_templates.py#L194-L195)
|
||||
|
||||
#### 实际应用场景
|
||||
|
||||
在临床手术科室的院感控制指标中,系统设置了"院感控制达标率"作为一票否决指标,确保医疗安全底线。
|
||||
|
||||
**章节来源**
|
||||
- [init_indicator_templates.py](file://backend/init_indicator_templates.py#L180-L196)
|
||||
|
||||
### 计算方法与考核方法的区别
|
||||
|
||||
系统明确区分了两种不同的指标处理方式:
|
||||
|
||||
#### 计算方法 (Calculation Method)
|
||||
- **定义**:用于计算实际值的具体公式或方法
|
||||
- **用途**:从原始数据中提取和计算指标的实际数值
|
||||
- **示例**:`(本期收入 - 同期收入)/同期收入 × 100%`
|
||||
|
||||
#### 考核方法 (Assessment Method)
|
||||
- **定义**:用于验证和确认指标结果的检查方法
|
||||
- **用途**:提供数据验证和审计依据
|
||||
- **示例**:统计报表、现场核查、问卷调查
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L130-L131)
|
||||
|
||||
### 指标与模板的关系
|
||||
|
||||
系统实现了指标与模板的多对多关系,支持灵活的指标配置:
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string code UK
|
||||
string name
|
||||
enum indicator_type
|
||||
enum bs_dimension
|
||||
numeric weight
|
||||
numeric max_score
|
||||
bool is_active
|
||||
}
|
||||
INDICATOR_TEMPLATES {
|
||||
int id PK
|
||||
string template_code UK
|
||||
string template_name
|
||||
enum template_type
|
||||
bool is_active
|
||||
}
|
||||
TEMPLATE_INDICATORS {
|
||||
int id PK
|
||||
int template_id FK
|
||||
int indicator_id FK
|
||||
string category
|
||||
numeric target_value
|
||||
string target_unit
|
||||
numeric weight
|
||||
string scoring_method
|
||||
text scoring_params
|
||||
int sort_order
|
||||
}
|
||||
INDICATORS ||--o{ TEMPLATE_INDICATORS : "被包含"
|
||||
INDICATOR_TEMPLATES ||--o{ TEMPLATE_INDICATORS : "包含"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L387-L438)
|
||||
- [002_template.py](file://backend/alembic/versions/002_template.py#L65-L95)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L411-L437)
|
||||
- [init_indicator_templates.py](file://backend/init_indicator_templates.py#L23-L200)
|
||||
|
||||
### 指标与考核明细的一对多关系
|
||||
|
||||
每个指标可以对应多个考核记录,形成完整的历史追踪:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Indicator {
|
||||
+int id
|
||||
+string code
|
||||
+string name
|
||||
+AssessmentDetail[] assessment_details
|
||||
}
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+string evidence
|
||||
+string remark
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentDetail[] details
|
||||
}
|
||||
Indicator "1" --> "0..*" AssessmentDetail : "被考核"
|
||||
Assessment "1" --> "0..*" AssessmentDetail : "包含"
|
||||
AssessmentDetail --> Indicator : "关联"
|
||||
AssessmentDetail --> Assessment : "属于"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L117-L146)
|
||||
- [models.py](file://backend/app/models/models.py#L181-L202)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L140-L141)
|
||||
- [models.py](file://backend/app/models/models.py#L195-L197)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
系统通过清晰的依赖关系实现模块化设计:
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
subgraph "外部依赖"
|
||||
SQLAlchemy[SQLAlchemy ORM]
|
||||
FastAPI[FastAPI框架]
|
||||
Pydantic[Pydantic验证]
|
||||
end
|
||||
subgraph "内部模块"
|
||||
Models[数据模型]
|
||||
Schemas[数据模式]
|
||||
Services[业务服务]
|
||||
API[API路由]
|
||||
end
|
||||
SQLAlchemy --> Models
|
||||
FastAPI --> API
|
||||
Pydantic --> Schemas
|
||||
Models --> Services
|
||||
Schemas --> Services
|
||||
Services --> API
|
||||
Models --> API
|
||||
Schemas --> API
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L8)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
系统在设计时充分考虑了性能优化:
|
||||
|
||||
### 数据库索引策略
|
||||
- 指标类型索引:加速指标类型的查询和筛选
|
||||
- 权重约束:确保数据完整性的同时维护性能
|
||||
- 多字段复合索引:优化复杂查询场景
|
||||
|
||||
### 缓存策略
|
||||
- 指标列表缓存:减少频繁的数据库查询
|
||||
- 模板数据缓存:提升模板导入和使用的响应速度
|
||||
|
||||
### 异步处理
|
||||
- 使用异步数据库连接:提高并发处理能力
|
||||
- 异步服务调用:避免阻塞操作影响整体性能
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题及解决方案
|
||||
|
||||
#### 指标编码重复错误
|
||||
**问题描述**:创建指标时提示编码已存在
|
||||
**解决方法**:检查指标编码的唯一性,确保每个编码在整个系统中唯一
|
||||
|
||||
#### 权重值异常
|
||||
**问题描述**:权重值小于等于0导致计算异常
|
||||
**解决方法**:确保权重值大于0,系统已通过数据库约束保证数据完整性
|
||||
|
||||
#### 一票否决触发
|
||||
**问题描述**:某些情况下指标得分为0分
|
||||
**解决方法**:检查一票否决条件的触发逻辑,确认是否符合预设的标准
|
||||
|
||||
**章节来源**
|
||||
- [indicators.py](file://backend/app/api/v1/indicators.py#L78-L81)
|
||||
- [models.py](file://backend/app/models/models.py#L144-L145)
|
||||
|
||||
## 结论
|
||||
|
||||
考核指标模型通过精心设计的架构和完善的约束机制,为医院绩效管理提供了坚实的技术基础。系统不仅支持灵活的指标配置和权重管理,还通过一票否决机制确保关键指标的严格执行。多对多关系的设计使得指标模板能够灵活复用,而清晰的计算方法与考核方法区分则保证了数据处理的准确性。
|
||||
|
||||
该模型的成功实施将有助于医院建立科学、公正、透明的绩效考核体系,为提升医疗质量和患者满意度提供有力支撑。
|
||||
470
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核明细模型.md
Normal file
470
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核明细模型.md
Normal file
@@ -0,0 +1,470 @@
|
||||
# 考核明细模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py)
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue)
|
||||
- [Assessments.vue](file://frontend/src/views/assessment/Assessments.vue)
|
||||
- [assessment.js](file://frontend/src/api/assessment.js)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
10. [附录](#附录)
|
||||
|
||||
## 简介
|
||||
|
||||
考核明细模型是医院绩效考核管理系统的核心数据结构,负责记录每个考核周期内员工各项指标的具体表现和得分情况。该模型实现了完整的考核数据管理功能,包括实际值记录、得分计算、佐证材料管理和多对一关系约束。
|
||||
|
||||
本系统采用现代化的技术栈,后端基于FastAPI和SQLAlchemy 2.0异步ORM,前端使用Vue 3 Composition API和Element Plus组件库,实现了完整的绩效考核流程管理。
|
||||
|
||||
## 项目结构
|
||||
|
||||
系统采用分层架构设计,主要包含以下层次:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "前端层"
|
||||
FE1[Assessments.vue<br/>考核列表页面]
|
||||
FE2[AssessmentDetail.vue<br/>考核详情页面]
|
||||
FE3[assessment.js<br/>API请求封装]
|
||||
end
|
||||
subgraph "后端层"
|
||||
BE1[assessments.py<br/>API路由]
|
||||
BE2[assessment_service.py<br/>业务服务层]
|
||||
BE3[schemas.py<br/>数据模式定义]
|
||||
end
|
||||
subgraph "数据层"
|
||||
DB1[models.py<br/>数据模型]
|
||||
DB2[001_initial.py<br/>数据库迁移]
|
||||
end
|
||||
FE1 --> FE3
|
||||
FE2 --> FE3
|
||||
FE3 --> BE1
|
||||
BE1 --> BE2
|
||||
BE2 --> BE3
|
||||
BE3 --> DB1
|
||||
DB1 --> DB2
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [Assessments.vue](file://frontend/src/views/assessment/Assessments.vue#L1-L311)
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L1-L257)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L263)
|
||||
- [models.py](file://backend/app/models/models.py#L181-L203)
|
||||
|
||||
**章节来源**
|
||||
- [Assessments.vue](file://frontend/src/views/assessment/Assessments.vue#L1-L311)
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L1-L257)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
## 核心组件
|
||||
|
||||
### AssessmentDetail模型设计
|
||||
|
||||
AssessmentDetail模型是考核明细的核心数据结构,具有以下关键特性:
|
||||
|
||||
**数据字段设计**:
|
||||
- `assessment_id`: 考核记录ID(外键关联)
|
||||
- `indicator_id`: 指标ID(外键关联)
|
||||
- `actual_value`: 实际值(数值型,支持小数)
|
||||
- `score`: 得分(数值型,默认0)
|
||||
- `evidence`: 佐证材料(文本型)
|
||||
- `remark`: 备注(文本型)
|
||||
|
||||
**关系映射**:
|
||||
- 与Assessment模型建立多对一关系
|
||||
- 与Indicator模型建立多对一关系
|
||||
- 支持级联删除和级联刷新
|
||||
|
||||
**索引优化**:
|
||||
- 为assessment_id和indicator_id建立复合索引
|
||||
- 提升查询性能和数据完整性
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L181-L203)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py#L114-L132)
|
||||
|
||||
### 考核流程集成
|
||||
|
||||
系统实现了完整的考核流程,AssessmentDetail模型在整个流程中发挥关键作用:
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant User as 用户
|
||||
participant Frontend as 前端界面
|
||||
participant API as API接口
|
||||
participant Service as 服务层
|
||||
participant DB as 数据库
|
||||
User->>Frontend : 输入实际值和得分
|
||||
Frontend->>API : 提交更新请求
|
||||
API->>Service : 调用更新方法
|
||||
Service->>DB : 更新AssessmentDetail记录
|
||||
DB-->>Service : 返回更新结果
|
||||
Service->>DB : 计算总分和加权得分
|
||||
DB-->>Service : 返回计算结果
|
||||
Service-->>API : 返回更新后的考核记录
|
||||
API-->>Frontend : 显示更新结果
|
||||
Frontend-->>User : 展示最新的考核明细
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L160-L175)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L111-L156)
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L160-L175)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用MVC架构模式,AssessmentDetail模型位于数据访问层,向上提供业务服务,向下连接数据库存储。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "表现层"
|
||||
UI1[Assessments.vue<br/>列表展示]
|
||||
UI2[AssessmentDetail.vue<br/>详情编辑]
|
||||
end
|
||||
subgraph "控制器层"
|
||||
API1[assessments.py<br/>路由处理]
|
||||
API2[authentication<br/>权限控制]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
SVC1[AssessmentService<br/>考核业务处理]
|
||||
SVC2[IndicatorService<br/>指标业务处理]
|
||||
end
|
||||
subgraph "数据访问层"
|
||||
MODEL1[Assessment模型]
|
||||
MODEL2[AssessmentDetail模型]
|
||||
MODEL3[Indicator模型]
|
||||
MODEL4[Staff模型]
|
||||
end
|
||||
subgraph "数据存储"
|
||||
DB1[PostgreSQL数据库]
|
||||
DB2[SQLAlchemy ORM]
|
||||
end
|
||||
UI1 --> API1
|
||||
UI2 --> API1
|
||||
API1 --> SVC1
|
||||
API1 --> SVC2
|
||||
SVC1 --> MODEL1
|
||||
SVC1 --> MODEL2
|
||||
SVC2 --> MODEL3
|
||||
MODEL1 --> DB2
|
||||
MODEL2 --> DB2
|
||||
MODEL3 --> DB2
|
||||
MODEL4 --> DB2
|
||||
DB2 --> DB1
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L203)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L14-L263)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### AssessmentDetail模型类图
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+string evidence
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+assessment Assessment
|
||||
+indicator Indicator
|
||||
}
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+string period_type
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+string status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
+datetime created_at
|
||||
+datetime updated_at
|
||||
+details AssessmentDetail[]
|
||||
}
|
||||
class Indicator {
|
||||
+int id
|
||||
+string name
|
||||
+string code
|
||||
+string indicator_type
|
||||
+float weight
|
||||
+float max_score
|
||||
+float target_value
|
||||
+string target_unit
|
||||
+string calculation_method
|
||||
+string assessment_method
|
||||
+string deduction_standard
|
||||
+string data_source
|
||||
+bool is_veto
|
||||
+bool is_active
|
||||
+details AssessmentDetail[]
|
||||
}
|
||||
AssessmentDetail --> Assessment : "多对一"
|
||||
AssessmentDetail --> Indicator : "多对一"
|
||||
Assessment "1" --> "*" AssessmentDetail : "一对多"
|
||||
Indicator "1" --> "*" AssessmentDetail : "一对多"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L203)
|
||||
|
||||
### 数据完整性约束
|
||||
|
||||
系统通过多种机制确保数据完整性:
|
||||
|
||||
**数据库层面约束**:
|
||||
- 主键约束:确保每条明细记录的唯一性
|
||||
- 外键约束:维护Assessment和Indicator的引用完整性
|
||||
- 检查约束:限制权重值必须大于0
|
||||
- 索引优化:提升查询性能
|
||||
|
||||
**业务层面约束**:
|
||||
- 状态机控制:严格的流程状态转换
|
||||
- 权限控制:不同角色的操作权限
|
||||
- 数据验证:输入数据的格式和范围检查
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L144-L146)
|
||||
- [models.py](file://backend/app/models/models.py#L199-L202)
|
||||
|
||||
### 得分计算算法
|
||||
|
||||
系统实现了灵活的得分计算机制:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始计算]) --> LoadDetails["加载考核明细"]
|
||||
LoadDetails --> CalcTotal["计算总分<br/>sum(score)"]
|
||||
CalcTotal --> CalcWeighted["计算加权得分<br/>sum(score × indicator.weight)"]
|
||||
CalcWeighted --> ValidateRange["验证分数范围<br/>0 ≤ score ≤ max_score"]
|
||||
ValidateRange --> CheckVeto{"检查一票否决"}
|
||||
CheckVeto --> |是| ApplyVeto["应用一票否决规则"]
|
||||
CheckVeto --> |否| CheckExceptions["检查异常值"]
|
||||
CheckVeto --> UpdateAssessment["更新考核记录"]
|
||||
ApplyVeto --> UpdateAssessment
|
||||
CheckExceptions --> UpdateAssessment
|
||||
UpdateAssessment --> End([计算完成])
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L74-L84)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L129-L149)
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L111-L156)
|
||||
|
||||
### 佐证材料管理
|
||||
|
||||
系统提供了完整的佐证材料管理功能:
|
||||
|
||||
**存储机制**:
|
||||
- 佐证材料以文本形式存储
|
||||
- 支持URL链接和文件路径
|
||||
- 可扩展为文件上传功能
|
||||
|
||||
**使用场景**:
|
||||
- 质量指标的证明材料
|
||||
- 数量指标的数据支撑
|
||||
- 效率指标的计算依据
|
||||
- 服务指标的客户反馈
|
||||
|
||||
**章节来源**
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L71-L82)
|
||||
- [models.py](file://backend/app/models/models.py#L190-L190)
|
||||
|
||||
### 时间戳跟踪机制
|
||||
|
||||
系统实现了全面的时间戳跟踪:
|
||||
|
||||
**创建时间**:记录AssessmentDetail的创建时刻
|
||||
**更新时间**:自动更新记录的修改时间
|
||||
**流程时间**:记录考核流程各阶段的时间戳
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 草稿
|
||||
草稿 --> 已提交 : 提交审核
|
||||
已提交 --> 已审核 : 审核通过
|
||||
已提交 --> 已驳回 : 审核驳回
|
||||
已审核 --> 已确认 : 确认考核
|
||||
已确认 --> [*]
|
||||
state 已提交 {
|
||||
[*] --> 提交时间记录
|
||||
}
|
||||
state 已审核 {
|
||||
[*] --> 审核时间记录
|
||||
}
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L163-L164)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L159-L170)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L163-L167)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L159-L192)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
系统各组件之间的依赖关系如下:
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
subgraph "外部依赖"
|
||||
A[FastAPI]
|
||||
B[SQLAlchemy 2.0]
|
||||
C[PostgreSQL]
|
||||
D[Vue 3]
|
||||
E[Element Plus]
|
||||
end
|
||||
subgraph "内部模块"
|
||||
F[models.py]
|
||||
G[assessment_service.py]
|
||||
H[assessments.py]
|
||||
I[schemas.py]
|
||||
J[AssessmentDetail.vue]
|
||||
K[Assessments.vue]
|
||||
end
|
||||
A --> H
|
||||
H --> G
|
||||
G --> F
|
||||
F --> C
|
||||
B --> F
|
||||
D --> J
|
||||
D --> K
|
||||
E --> J
|
||||
E --> K
|
||||
J --> I
|
||||
K --> I
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L12)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L16)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L12)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 查询优化策略
|
||||
|
||||
**索引设计**:
|
||||
- 为assessment_id和indicator_id建立复合索引
|
||||
- 为常用查询条件建立单独索引
|
||||
- 使用覆盖索引减少查询开销
|
||||
|
||||
**查询优化**:
|
||||
- 使用selectinload进行关联查询
|
||||
- 避免N+1查询问题
|
||||
- 实施分页查询机制
|
||||
|
||||
### 缓存策略
|
||||
|
||||
**数据缓存**:
|
||||
- 指标配置信息缓存
|
||||
- 员工基本信息缓存
|
||||
- 科室层级结构缓存
|
||||
|
||||
**查询结果缓存**:
|
||||
- 统计报表结果缓存
|
||||
- 常用查询结果缓存
|
||||
- 配置信息缓存
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题及解决方案
|
||||
|
||||
**数据同步问题**:
|
||||
- 确保Assessment和AssessmentDetail的事务一致性
|
||||
- 检查外键约束是否正确设置
|
||||
- 验证数据类型和精度匹配
|
||||
|
||||
**性能问题**:
|
||||
- 分析慢查询日志
|
||||
- 检查索引使用情况
|
||||
- 优化复杂查询语句
|
||||
|
||||
**权限问题**:
|
||||
- 验证用户角色和权限
|
||||
- 检查API访问控制
|
||||
- 确认数据访问范围
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L117-L118)
|
||||
- [models.py](file://backend/app/models/models.py#L199-L202)
|
||||
|
||||
## 结论
|
||||
|
||||
考核明细模型作为医院绩效考核管理系统的核心组件,实现了完整的数据管理功能。通过合理的数据结构设计、严格的数据完整性约束和高效的性能优化策略,系统能够满足医院复杂的绩效考核需求。
|
||||
|
||||
该模型不仅支持基本的考核数据记录,还提供了灵活的扩展能力,可以适应不同科室和岗位的考核要求。同时,系统的权限控制和审计功能确保了数据的安全性和可追溯性。
|
||||
|
||||
## 附录
|
||||
|
||||
### 数据录入示例
|
||||
|
||||
**单个明细录入**:
|
||||
1. 选择考核周期(年、月)
|
||||
2. 选择员工和指标
|
||||
3. 录入实际值和得分
|
||||
4. 添加佐证材料
|
||||
5. 保存并提交审核
|
||||
|
||||
**批量处理方法**:
|
||||
1. 通过批量创建功能生成默认明细
|
||||
2. 批量导入实际值数据
|
||||
3. 统一审核和确认流程
|
||||
4. 生成批量统计报告
|
||||
|
||||
### 数据质量保证措施
|
||||
|
||||
**数据验证规则**:
|
||||
- 分数范围验证(0-max_score)
|
||||
- 权重有效性检查
|
||||
- 指标类型匹配验证
|
||||
- 时间范围合理性检查
|
||||
|
||||
**异常值处理**:
|
||||
- 设置合理的阈值范围
|
||||
- 异常值标记和提醒
|
||||
- 自动化异常检测机制
|
||||
- 人工复核流程
|
||||
|
||||
**章节来源**
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L196-L218)
|
||||
- [AssessmentDetail.vue](file://frontend/src/views/assessment/AssessmentDetail.vue#L47-L68)
|
||||
504
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核记录模型.md
Normal file
504
.qoder/repowiki/zh/content/数据模型详解/核心数据模型/考核记录模型.md
Normal file
@@ -0,0 +1,504 @@
|
||||
# 考核记录模型
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [models.py](file://backend/app/models/models.py)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py)
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [001_initial.py](file://backend/alembic/versions/001_initial.py)
|
||||
- [assessment.js](file://frontend/src/api/assessment.js)
|
||||
- [database.md](file://docs/database.md)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
|
||||
考核记录模型是医院绩效管理系统的核心数据结构,负责管理员工的绩效考核过程。该模型实现了完整的多级审批流程,支持草稿→提交→审核→确认→驳回的状态流转,并提供了灵活的考核周期管理和数据一致性保证机制。
|
||||
|
||||
## 项目结构
|
||||
|
||||
后端采用典型的三层架构设计,主要包含以下层次:
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "表现层"
|
||||
API[API路由层]
|
||||
Frontend[前端接口]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
Service[服务层]
|
||||
Schema[数据模式层]
|
||||
end
|
||||
subgraph "数据访问层"
|
||||
Model[模型层]
|
||||
DB[(数据库)]
|
||||
end
|
||||
Frontend --> API
|
||||
API --> Service
|
||||
Service --> Model
|
||||
Model --> DB
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L14-L263)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L263)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
## 核心组件
|
||||
|
||||
### 考核状态枚举
|
||||
|
||||
考核状态枚举定义了完整的审批流程状态:
|
||||
|
||||
```mermaid
|
||||
stateDiagram-v2
|
||||
[*] --> 草稿
|
||||
草稿 --> 已提交 : 提交考核
|
||||
已提交 --> 已审核 : 审核通过
|
||||
已提交 --> 已驳回 : 审核驳回
|
||||
已审核 --> 已确认 : 确认完成
|
||||
已确认 --> [*]
|
||||
已驳回 --> 草稿 : 修改后重新提交
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L45-L51)
|
||||
|
||||
### 主要数据模型
|
||||
|
||||
系统包含四个核心数据模型,形成了完整的考核数据结构:
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
ASSESSMENTS {
|
||||
int id PK
|
||||
int staff_id FK
|
||||
int period_year
|
||||
int period_month
|
||||
string period_type
|
||||
float total_score
|
||||
float weighted_score
|
||||
string status
|
||||
int assessor_id FK
|
||||
int reviewer_id FK
|
||||
datetime submit_time
|
||||
datetime review_time
|
||||
text remark
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
ASSESSMENT_DETAILS {
|
||||
int id PK
|
||||
int assessment_id FK
|
||||
int indicator_id FK
|
||||
float actual_value
|
||||
float score
|
||||
text evidence
|
||||
text remark
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
STAFF {
|
||||
int id PK
|
||||
int employee_id UK
|
||||
string name
|
||||
int department_id FK
|
||||
string position
|
||||
string title
|
||||
string phone
|
||||
string email
|
||||
float base_salary
|
||||
float performance_ratio
|
||||
string status
|
||||
datetime hire_date
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
string indicator_type
|
||||
float weight
|
||||
float max_score
|
||||
float target_value
|
||||
string target_unit
|
||||
text calculation_method
|
||||
text assessment_method
|
||||
text deduction_standard
|
||||
string data_source
|
||||
string applicable_dept_types
|
||||
boolean is_veto
|
||||
boolean is_active
|
||||
datetime created_at
|
||||
datetime updated_at
|
||||
}
|
||||
ASSESSMENTS ||--o{ ASSESSMENT_DETAILS : contains
|
||||
STAFF ||--o{ ASSESSMENTS : evaluates
|
||||
INDICATORS ||--o{ ASSESSMENT_DETAILS : measures
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L203)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L203)
|
||||
|
||||
## 架构概览
|
||||
|
||||
系统采用RESTful API设计,实现了完整的CRUD操作和业务流程控制:
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as 客户端
|
||||
participant API as API层
|
||||
participant Service as 服务层
|
||||
participant DB as 数据库
|
||||
Client->>API : 创建考核请求
|
||||
API->>Service : create_assessment()
|
||||
Service->>DB : 插入Assessment记录
|
||||
Service->>DB : 插入AssessmentDetail记录
|
||||
DB-->>Service : 返回新记录ID
|
||||
Service-->>API : 返回创建结果
|
||||
API-->>Client : 返回创建成功
|
||||
Client->>API : 提交考核请求
|
||||
API->>Service : submit_assessment()
|
||||
Service->>DB : 更新状态为SUBMITTED
|
||||
DB-->>Service : 确认更新
|
||||
Service-->>API : 返回提交结果
|
||||
API-->>Client : 返回提交成功
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L80-L115)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### Assessment模型详解
|
||||
|
||||
Assessment模型是整个考核系统的核心,包含了完整的考核信息和审批状态:
|
||||
|
||||
#### 字段设计
|
||||
|
||||
| 字段名 | 类型 | 描述 | 约束 |
|
||||
|--------|------|------|------|
|
||||
| id | Integer | 主键ID | 自增 |
|
||||
| staff_id | Integer | 员工ID | 外键,必填 |
|
||||
| period_year | Integer | 考核年度 | 必填,范围2020-2100 |
|
||||
| period_month | Integer | 考核月份 | 必填,范围1-12 |
|
||||
| period_type | String | 考核周期类型 | 默认monthly |
|
||||
| total_score | Float | 总分 | 默认0 |
|
||||
| weighted_score | Float | 加权得分 | 默认0 |
|
||||
| status | Enum | 考核状态 | 默认DRAFT |
|
||||
| assessor_id | Integer | 考核人ID | 外键,可选 |
|
||||
| reviewer_id | Integer | 审核人ID | 外键,可选 |
|
||||
| submit_time | DateTime | 提交时间 | 可选 |
|
||||
| review_time | DateTime | 审核时间 | 可选 |
|
||||
| remark | Text | 备注 | 可选 |
|
||||
|
||||
#### 关系映射
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class Assessment {
|
||||
+int id
|
||||
+int staff_id
|
||||
+int period_year
|
||||
+int period_month
|
||||
+float total_score
|
||||
+float weighted_score
|
||||
+AssessmentStatus status
|
||||
+int assessor_id
|
||||
+int reviewer_id
|
||||
+datetime submit_time
|
||||
+datetime review_time
|
||||
+string remark
|
||||
+staff : Staff
|
||||
+assessor : Staff
|
||||
+reviewer : Staff
|
||||
+details : AssessmentDetail[]
|
||||
}
|
||||
class Staff {
|
||||
+int id
|
||||
+string employee_id
|
||||
+string name
|
||||
+int department_id
|
||||
+string position
|
||||
+assessments : Assessment[]
|
||||
}
|
||||
class AssessmentDetail {
|
||||
+int id
|
||||
+int assessment_id
|
||||
+int indicator_id
|
||||
+float actual_value
|
||||
+float score
|
||||
+assessment : Assessment
|
||||
+indicator : Indicator
|
||||
}
|
||||
Assessment --> Staff : belongs_to
|
||||
Assessment --> Staff : evaluated_by
|
||||
Assessment --> Staff : reviewed_by
|
||||
Assessment --> AssessmentDetail : has_many
|
||||
AssessmentDetail --> Indicator : measures
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L149-L173)
|
||||
|
||||
#### 状态流转机制
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> Draft["草稿状态<br/>DRAFT"]
|
||||
Draft --> Submit["提交状态<br/>SUBMITTED"]
|
||||
Submit --> Review["审核状态<br/>REVIEWED"]
|
||||
Submit --> Reject["驳回状态<br/>REJECTED"]
|
||||
Review --> Finalize["确认状态<br/>FINALIZED"]
|
||||
Reject --> Draft2["返回草稿<br/>DRAFT"]
|
||||
Finalize --> End([结束])
|
||||
Draft2 --> Submit
|
||||
style Draft fill:#e1f5fe
|
||||
style Submit fill:#f3e5f5
|
||||
style Review fill:#e8f5e8
|
||||
style Reject fill:#ffebee
|
||||
style Finalize fill:#fff3e0
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L159-L205)
|
||||
|
||||
### 计算逻辑实现
|
||||
|
||||
#### 总分计算
|
||||
|
||||
总分计算逻辑简单直接,将所有考核明细的得分相加:
|
||||
|
||||
```python
|
||||
# 总分 = Σ(明细得分)
|
||||
total_score = sum(d.score for d in assessment_data.details)
|
||||
```
|
||||
|
||||
#### 加权得分计算
|
||||
|
||||
加权得分考虑了指标权重的影响:
|
||||
|
||||
```python
|
||||
# 加权得分 = Σ(明细得分 × 指标权重)
|
||||
weighted_score = 0.0
|
||||
for detail in assessment_data.details:
|
||||
indicator = await db.execute(
|
||||
select(Indicator).where(Indicator.id == detail.indicator_id)
|
||||
)
|
||||
ind = indicator.scalar_one_or_none()
|
||||
if ind:
|
||||
weighted_score += detail.score * float(ind.weight)
|
||||
```
|
||||
|
||||
**章节来源**
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L71-L108)
|
||||
|
||||
### API接口设计
|
||||
|
||||
系统提供了完整的RESTful API接口:
|
||||
|
||||
| 方法 | 路径 | 功能 | 权限要求 |
|
||||
|------|------|------|----------|
|
||||
| GET | /assessments | 获取考核列表 | 任意用户 |
|
||||
| GET | /assessments/{id} | 获取考核详情 | 任意用户 |
|
||||
| POST | /assessments | 创建考核记录 | 普通用户 |
|
||||
| PUT | /assessments/{id} | 更新考核记录 | 普通用户 |
|
||||
| POST | /assessments/{id}/submit | 提交考核 | 普通用户 |
|
||||
| POST | /assessments/{id}/review | 审核考核 | 管理员/经理 |
|
||||
| POST | /assessments/{id}/finalize | 确认考核 | 管理员/经理 |
|
||||
| POST | /assessments/batch-create | 批量创建考核 | 管理员/经理 |
|
||||
|
||||
**章节来源**
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
### 数据一致性保证
|
||||
|
||||
#### 级联删除机制
|
||||
|
||||
Assessment模型使用了级联删除策略,确保当主记录被删除时,相关的明细记录也会自动清理:
|
||||
|
||||
```python
|
||||
details: Mapped[List["AssessmentDetail"]] = relationship(
|
||||
"AssessmentDetail",
|
||||
back_populates="assessment",
|
||||
cascade="all, delete-orphan"
|
||||
)
|
||||
```
|
||||
|
||||
#### 索引优化
|
||||
|
||||
数据库层面建立了多个索引以提升查询性能:
|
||||
|
||||
- `idx_assessment_staff`: 员工ID索引
|
||||
- `idx_assessment_period`: 年度+月份复合索引
|
||||
- `idx_assessment_status`: 状态索引
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L174-L178)
|
||||
|
||||
## 依赖关系分析
|
||||
|
||||
### 模块间依赖
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
subgraph "外部依赖"
|
||||
SQLAlchemy[SQLAlchemy ORM]
|
||||
FastAPI[FastAPI框架]
|
||||
Pydantic[Pydantic验证]
|
||||
end
|
||||
subgraph "内部模块"
|
||||
Models[数据模型]
|
||||
Services[业务服务]
|
||||
API[API路由]
|
||||
Schemas[数据模式]
|
||||
end
|
||||
SQLAlchemy --> Models
|
||||
FastAPI --> API
|
||||
Pydantic --> Schemas
|
||||
API --> Services
|
||||
Services --> Models
|
||||
API --> Schemas
|
||||
Services --> Schemas
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L13)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L11)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L15)
|
||||
|
||||
### 数据流依赖
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Request[HTTP请求] --> Validation[数据验证]
|
||||
Validation --> ServiceCall[服务调用]
|
||||
ServiceCall --> DBQuery[数据库查询]
|
||||
DBQuery --> BusinessLogic[业务逻辑处理]
|
||||
BusinessLogic --> DBUpdate[数据库更新]
|
||||
DBUpdate --> Response[响应生成]
|
||||
Response --> Client[客户端]
|
||||
Validation --> |Schema验证| ServiceCall
|
||||
BusinessLogic --> |状态检查| DBUpdate
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [schemas.py](file://backend/app/schemas/schemas.py#L220-L237)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L111-L156)
|
||||
|
||||
**章节来源**
|
||||
- [models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [assessment_service.py](file://backend/app/services/assessment_service.py#L1-L263)
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
### 查询优化
|
||||
|
||||
1. **索引策略**: 为常用查询字段建立索引,包括员工ID、考核周期、状态等
|
||||
2. **延迟加载**: 使用selectinload优化N+1查询问题
|
||||
3. **分页处理**: 支持大数据集的分页查询
|
||||
|
||||
### 缓存策略
|
||||
|
||||
虽然当前实现没有内置缓存,但可以考虑:
|
||||
- 考核状态的热点数据缓存
|
||||
- 指标权重的静态数据缓存
|
||||
- 员工基本信息的短期缓存
|
||||
|
||||
### 批量操作
|
||||
|
||||
系统支持批量创建考核记录,适用于月末批量处理场景:
|
||||
|
||||
```python
|
||||
# 批量创建逻辑
|
||||
for staff in staff_list:
|
||||
assessment = Assessment(staff_id=staff.id, ...)
|
||||
db.add(assessment)
|
||||
# 为每个指标创建明细
|
||||
for indicator_id in indicators:
|
||||
detail = AssessmentDetail(indicator_id=indicator_id, ...)
|
||||
db.add(detail)
|
||||
```
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
### 常见问题及解决方案
|
||||
|
||||
#### 状态流转错误
|
||||
|
||||
**问题**: 无法从草稿状态提交
|
||||
**原因**: 考核记录状态不是DRAFT
|
||||
**解决方案**: 检查当前状态是否为DRAFT
|
||||
|
||||
#### 权限不足
|
||||
|
||||
**问题**: 审核或确认接口返回400错误
|
||||
**原因**: 当前用户权限不足
|
||||
**解决方案**: 确保用户具有管理员或经理权限
|
||||
|
||||
#### 数据重复
|
||||
|
||||
**问题**: 批量创建时出现重复记录
|
||||
**原因**: 同一员工在同一考核周期已存在记录
|
||||
**解决方案**: 系统会自动跳过已存在的记录
|
||||
|
||||
### 异常处理机制
|
||||
|
||||
系统采用统一的异常处理模式:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Try[业务操作] --> Success{操作成功?}
|
||||
Success --> |是| ReturnOK[返回成功响应]
|
||||
Success --> |否| CheckError{检查错误类型}
|
||||
CheckError --> |业务错误| Return400[返回400错误]
|
||||
CheckError --> |权限错误| Return403[返回403错误]
|
||||
CheckError --> |数据库错误| Return500[返回500错误]
|
||||
CheckError --> |其他错误| ReturnError[返回通用错误]
|
||||
Return400 --> Catch[异常捕获]
|
||||
Return403 --> Catch
|
||||
Return500 --> Catch
|
||||
ReturnError --> Catch
|
||||
Catch --> Log[记录日志]
|
||||
Log --> ReturnError
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L105-L132)
|
||||
|
||||
**章节来源**
|
||||
- [assessments.py](file://backend/app/api/v1/assessments.py#L105-L132)
|
||||
|
||||
## 结论
|
||||
|
||||
考核记录模型设计合理,实现了以下关键特性:
|
||||
|
||||
1. **完整的审批流程**: 支持多级审批的完整生命周期管理
|
||||
2. **灵活的数据模型**: 支持多种考核周期和指标类型
|
||||
3. **强一致性的数据结构**: 通过外键约束和级联删除保证数据完整性
|
||||
4. **良好的扩展性**: 模块化设计便于功能扩展和维护
|
||||
5. **完善的API接口**: 提供RESTful风格的完整接口集合
|
||||
|
||||
该模型为医院绩效管理系统的稳定运行奠定了坚实的数据基础,能够有效支撑复杂的绩效考核业务需求。
|
||||
403
.qoder/repowiki/zh/content/数据模型详解/模型验证规则.md
Normal file
403
.qoder/repowiki/zh/content/数据模型详解/模型验证规则.md
Normal file
@@ -0,0 +1,403 @@
|
||||
# 模型验证规则
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py)
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py)
|
||||
- [backend/app/api/v1/assessments.py](file://backend/app/api/v1/assessments.py)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py)
|
||||
- [backend/app/services/indicator_service.py](file://backend/app/services/indicator_service.py)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py)
|
||||
- [backend/app/main.py](file://backend/app/main.py)
|
||||
- [backend/requirements.txt](file://backend/requirements.txt)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [简介](#简介)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概览](#架构概览)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 简介
|
||||
本文件系统性梳理了医院绩效系统中的模型验证规则,涵盖数据模型的验证机制,包括字段类型验证、范围限制、格式检查和业务规则验证。文档重点解释了以下三个层面的验证实现:
|
||||
- Pydantic 模型验证:通过 Pydantic 的 Field 参数与类型注解实现请求体与响应体的数据校验。
|
||||
- SQLAlchemy 约束验证:通过数据库层的列类型、索引与 CheckConstraint 实现数据完整性约束。
|
||||
- 业务逻辑验证:通过服务层与 API 层的业务规则检查,确保数据在业务语义上的正确性。
|
||||
|
||||
同时,文档阐述了验证错误的处理方式与用户友好的错误信息设计,并提供验证规则的扩展方法与自定义验证器的实现建议。
|
||||
|
||||
## 项目结构
|
||||
后端采用 FastAPI + SQLAlchemy 异步 ORM 的架构,数据模型位于 models 目录,Pydantic 数据模式位于 schemas 目录,API 路由位于 api/v1 目录,业务逻辑位于 services 目录,异常处理与全局配置位于 main.py。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "API 层"
|
||||
A1["staff.py"]
|
||||
A2["indicators.py"]
|
||||
A3["assessments.py"]
|
||||
end
|
||||
subgraph "服务层"
|
||||
S1["staff_service.py"]
|
||||
S2["indicator_service.py"]
|
||||
S3["assessment_service.py"]
|
||||
end
|
||||
subgraph "模式层"
|
||||
P1["schemas.py"]
|
||||
end
|
||||
subgraph "模型层"
|
||||
M1["models.py"]
|
||||
M2["finance.py"]
|
||||
end
|
||||
subgraph "核心"
|
||||
C1["main.py"]
|
||||
C2["requirements.txt"]
|
||||
end
|
||||
A1 --> S1
|
||||
A2 --> S2
|
||||
A3 --> S3
|
||||
S1 --> M1
|
||||
S2 --> M1
|
||||
S3 --> M1
|
||||
A1 --> P1
|
||||
A2 --> P1
|
||||
A3 --> P1
|
||||
M1 --> C2
|
||||
M2 --> C2
|
||||
P1 --> C2
|
||||
C1 --> A1
|
||||
C1 --> A2
|
||||
C1 --> A3
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L1-L124)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py#L1-L142)
|
||||
- [backend/app/api/v1/assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [backend/app/services/indicator_service.py](file://backend/app/services/indicator_service.py#L1-L197)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py#L114-L262)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py#L1-L79)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L50-L91)
|
||||
- [backend/requirements.txt](file://backend/requirements.txt#L1-L16)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L1-L124)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py#L1-L142)
|
||||
- [backend/app/api/v1/assessments.py](file://backend/app/api/v1/assessments.py#L1-L166)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py#L1-L112)
|
||||
- [backend/app/services/indicator_service.py](file://backend/app/services/indicator_service.py#L1-L197)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py#L114-L262)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L1-L743)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L1-L438)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py#L1-L79)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L50-L91)
|
||||
- [backend/requirements.txt](file://backend/requirements.txt#L1-L16)
|
||||
|
||||
## 核心组件
|
||||
- Pydantic 数据模式:通过 Field 的类型、长度、数值范围、正则表达式等参数实现字段级验证;通过枚举类型保证取值域的正确性;通过 model_config 的 from_attributes 控制 ORM 对象到 Pydantic 模式的转换。
|
||||
- SQLAlchemy 模型:通过列类型(String、Integer、Numeric、Boolean、DateTime、Enum)、索引与 CheckConstraint 实现数据库层约束;通过外键关系与级联策略保证参照完整性。
|
||||
- API 层:在路由函数中接收 Pydantic 模式作为请求体,自动触发 Pydantic 验证;在业务逻辑允许范围内进行额外的业务规则检查,并抛出 HTTP 异常。
|
||||
- 服务层:封装 CRUD 与业务逻辑,负责数据一致性与业务规则的执行;在必要时进行跨实体的约束检查。
|
||||
- 异常处理:全局注册异常处理器,捕获并记录验证错误与业务异常,返回统一的错误信息。
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L49-L60)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L62-L85)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L68-L81)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py#L69-L91)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L58-L74)
|
||||
|
||||
## 架构概览
|
||||
下图展示了从 API 请求到数据库写入的完整验证链路,包括 Pydantic 验证、业务规则检查与数据库约束验证。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant Client as "客户端"
|
||||
participant API as "API 路由"
|
||||
participant Pyd as "Pydantic 模式"
|
||||
participant Svc as "服务层"
|
||||
participant DB as "SQLAlchemy 模型"
|
||||
participant SQL as "数据库"
|
||||
Client->>API : "POST /staff"
|
||||
API->>Pyd : "StaffCreate 验证"
|
||||
Pyd-->>API : "验证通过/错误"
|
||||
API->>Svc : "调用业务逻辑"
|
||||
Svc->>DB : "构造模型实例"
|
||||
DB->>SQL : "执行插入/更新"
|
||||
SQL-->>DB : "约束检查结果"
|
||||
DB-->>Svc : "返回持久化结果"
|
||||
Svc-->>API : "返回业务结果"
|
||||
API-->>Client : "统一响应"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L68-L81)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L107-L124)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py#L69-L76)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L88-L114)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### Pydantic 模型验证
|
||||
- 字段类型与长度验证:通过 Field 的类型注解与 max_length/min_length 限制字符串长度;例如员工工号、姓名、职位、电话、邮箱等字段均设置了长度限制。
|
||||
- 数值范围验证:通过 ge(大于等于)、le(小于等于)、gt(大于)等参数限制数值范围;例如基本工资、绩效系数、权重、最高分值、年份、月份等。
|
||||
- 枚举验证:通过 str + Enum 的组合确保取值域的正确性;例如科室类型、员工状态、指标类型、考核状态等。
|
||||
- 正则表达式验证:通过 pattern 参数对字符串格式进行约束;例如用户角色字段使用正则限制合法取值。
|
||||
- 响应模式转换:通过 model_config(from_attributes=True) 将 ORM 对象直接转换为 Pydantic 模式,避免重复映射。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class StaffBase {
|
||||
+employee_id : str
|
||||
+name : str
|
||||
+department_id : int
|
||||
+position : str
|
||||
+title : Optional[str]
|
||||
+phone : Optional[str]
|
||||
+email : Optional[str]
|
||||
+base_salary : float
|
||||
+performance_ratio : float
|
||||
}
|
||||
class StaffCreate {
|
||||
+status : StaffStatus
|
||||
+hire_date : Optional[datetime]
|
||||
}
|
||||
class StaffResponse {
|
||||
+id : int
|
||||
+status : StaffStatus
|
||||
+hire_date : Optional[datetime]
|
||||
+created_at : datetime
|
||||
+updated_at : datetime
|
||||
+department_name : Optional[str]
|
||||
}
|
||||
StaffCreate --|> StaffBase
|
||||
StaffResponse --|> StaffBase
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L107-L150)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L64-L98)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L107-L150)
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L315-L345)
|
||||
|
||||
### SQLAlchemy 约束验证
|
||||
- 列类型与默认值:通过 String、Integer、Numeric、Boolean、DateTime、Enum 等类型定义字段属性与默认值;例如 Numeric(10,2) 用于金额与分数的精确存储。
|
||||
- 索引优化:为常用查询字段添加索引,提升查询性能;例如科室类型、状态、年月组合等。
|
||||
- CheckConstraint:通过 CheckConstraint 在数据库层强制业务约束;例如指标权重必须大于 0,财务金额必须大于等于 0。
|
||||
- 外键关系:通过 ForeignKey 建立实体间的参照关系,配合级联策略保证数据一致性。
|
||||
|
||||
```mermaid
|
||||
erDiagram
|
||||
STAFF {
|
||||
int id PK
|
||||
string employee_id UK
|
||||
string name
|
||||
int department_id FK
|
||||
string position
|
||||
string title
|
||||
string phone
|
||||
string email
|
||||
numeric base_salary
|
||||
numeric performance_ratio
|
||||
enum status
|
||||
date hire_date
|
||||
}
|
||||
DEPARTMENTS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
enum dept_type
|
||||
int parent_id FK
|
||||
int level
|
||||
int sort_order
|
||||
boolean is_active
|
||||
}
|
||||
INDICATORS {
|
||||
int id PK
|
||||
string name
|
||||
string code UK
|
||||
enum indicator_type
|
||||
enum bs_dimension
|
||||
numeric weight
|
||||
numeric max_score
|
||||
numeric target_value
|
||||
string target_unit
|
||||
text calculation_method
|
||||
text assessment_method
|
||||
text deduction_standard
|
||||
text data_source
|
||||
string applicable_dept_types
|
||||
boolean is_veto
|
||||
boolean is_active
|
||||
}
|
||||
ASSESSMENTS {
|
||||
int id PK
|
||||
int staff_id FK
|
||||
int period_year
|
||||
int period_month
|
||||
string period_type
|
||||
numeric total_score
|
||||
numeric weighted_score
|
||||
enum status
|
||||
int assessor_id FK
|
||||
int reviewer_id FK
|
||||
datetime submit_time
|
||||
datetime review_time
|
||||
text remark
|
||||
}
|
||||
ASSESSMENT_DETAILS {
|
||||
int id PK
|
||||
int assessment_id FK
|
||||
int indicator_id FK
|
||||
numeric actual_value
|
||||
numeric score
|
||||
text evidence
|
||||
text remark
|
||||
}
|
||||
SALARY_RECORDS {
|
||||
int id PK
|
||||
int staff_id FK
|
||||
int period_year
|
||||
int period_month
|
||||
numeric base_salary
|
||||
numeric performance_score
|
||||
numeric performance_bonus
|
||||
numeric deduction
|
||||
numeric allowance
|
||||
numeric total_salary
|
||||
string status
|
||||
text remark
|
||||
}
|
||||
DEPARTMENTS ||--o{ STAFF : "拥有"
|
||||
STAFF ||--o{ ASSESSMENTS : "被考核"
|
||||
ASSESSMENTS ||--o{ ASSESSMENT_DETAILS : "包含"
|
||||
INDICATORS ||--o{ ASSESSMENT_DETAILS : "被评分"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L62-L114)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L117-L146)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L149-L178)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L181-L202)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L205-L230)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py#L45-L74)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L143-L146)
|
||||
- [backend/app/models/finance.py](file://backend/app/models/finance.py#L68-L74)
|
||||
|
||||
### 业务逻辑验证
|
||||
- API 层业务规则:在创建与更新接口中,先进行 Pydantic 验证,再进行业务规则检查;例如创建员工前检查工号唯一性,创建指标前检查编码唯一性。
|
||||
- 服务层业务规则:在服务层进行更复杂的业务一致性检查;例如更新考核记录时,仅允许在草稿或已驳回状态下进行修改,并重新计算总分与加权分。
|
||||
- 统一错误处理:通过 HTTPException 抛出业务错误,结合全局异常处理器记录日志并返回统一的错误响应。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start(["开始"]) --> ValidatePyd["Pydantic 验证"]
|
||||
ValidatePyd --> PydanticOK{"验证通过?"}
|
||||
PydanticOK --> |否| ReturnError["返回验证错误"]
|
||||
PydanticOK --> |是| BusinessCheck["业务规则检查"]
|
||||
BusinessCheck --> BusinessOK{"业务规则通过?"}
|
||||
BusinessOK --> |否| RaiseHTTP["抛出 HTTP 异常"]
|
||||
BusinessOK --> |是| Persist["持久化到数据库"]
|
||||
Persist --> Done(["结束"])
|
||||
ReturnError --> Done
|
||||
RaiseHTTP --> Done
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L75-L78)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py#L78-L81)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py#L114-L151)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L58-L74)
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L68-L95)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py#L71-L98)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py#L114-L151)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L58-L74)
|
||||
|
||||
### 验证错误处理与用户友好信息
|
||||
- HTTP 异常:在业务规则不满足时,使用 HTTPException 返回明确的状态码与错误信息,如“员工不存在”、“工号已存在”、“指标不存在”等。
|
||||
- 统一响应结构:API 返回统一的响应结构,包含状态码、消息、数据、分页信息等,便于前端展示与调试。
|
||||
- 全局异常处理:注册 RequestValidationError 与 StarletteHTTPException 的处理器,记录错误日志并向上抛出,确保错误信息一致且可追踪。
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L60-L61)
|
||||
- [backend/app/api/v1/indicators.py](file://backend/app/api/v1/indicators.py#L66-L67)
|
||||
- [backend/app/api/v1/assessments.py](file://backend/app/api/v1/assessments.py#L99-L101)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L58-L74)
|
||||
|
||||
### 验证规则扩展与自定义验证器
|
||||
- 扩展 Pydantic 验证:可在现有 Field 参数基础上增加更多约束,如自定义正则表达式、长度范围、数值边界等;对于复杂字段(如 JSON),可使用 Json 类型与自定义解析器。
|
||||
- 自定义验证器:可通过 Pydantic 的 field_validator 或 root_validator 实现跨字段验证与复杂业务规则;例如在创建考核时,验证明细中的指标权重与总分计算的一致性。
|
||||
- 数据库约束增强:在模型层新增 CheckConstraint 或复合索引,以强化数据完整性;例如为“员工工号+部门”的唯一性约束添加复合索引。
|
||||
- 业务规则扩展:在服务层增加新的业务规则检查点,如在创建考核时检查指标是否适用于当前科室类型、是否启用等。
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/schemas/schemas.py](file://backend/app/schemas/schemas.py#L153-L192)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L143-L146)
|
||||
- [backend/app/services/assessment_service.py](file://backend/app/services/assessment_service.py#L114-L151)
|
||||
|
||||
## 依赖关系分析
|
||||
- 版本要求:项目使用 FastAPI、SQLAlchemy、Pydantic 等核心依赖,版本在 requirements.txt 中声明,确保验证与 ORM 功能的稳定性。
|
||||
- 模块间耦合:API 层依赖 Pydantic 模式与服务层;服务层依赖 SQLAlchemy 模型;模型层依赖数据库驱动与 Alembic 迁移工具。
|
||||
- 异常处理:全局异常处理器统一处理验证与业务异常,减少重复代码并提升用户体验。
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
Req["requirements.txt"] --> FastAPI["FastAPI"]
|
||||
Req --> SQLAlchemy["SQLAlchemy"]
|
||||
Req --> Pydantic["Pydantic"]
|
||||
API["API 路由"] --> PydanticSchema["Pydantic 模式"]
|
||||
API --> Service["服务层"]
|
||||
Service --> Model["SQLAlchemy 模型"]
|
||||
Model --> DB["数据库"]
|
||||
Main["main.py"] --> API
|
||||
Main --> Service
|
||||
Main --> Model
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [backend/requirements.txt](file://backend/requirements.txt#L1-L16)
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L10-L15)
|
||||
- [backend/app/services/staff_service.py](file://backend/app/services/staff_service.py#L9-L10)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L13-L13)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L50-L77)
|
||||
|
||||
**章节来源**
|
||||
- [backend/requirements.txt](file://backend/requirements.txt#L1-L16)
|
||||
- [backend/app/main.py](file://backend/app/main.py#L50-L77)
|
||||
|
||||
## 性能考虑
|
||||
- 索引优化:为高频查询字段(如科室类型、状态、年月组合)建立索引,降低查询成本。
|
||||
- 数值精度:使用 Numeric 类型存储金额与分数,避免浮点误差;合理设置精度与小数位数。
|
||||
- 查询优化:在服务层使用 selectinload 等策略预加载关联对象,减少 N+1 查询问题。
|
||||
- 异步 I/O:利用 SQLAlchemy 异步引擎与 FastAPI 的异步特性,提升并发处理能力。
|
||||
|
||||
## 故障排除指南
|
||||
- Pydantic 验证失败:检查请求体字段类型、长度与范围是否符合模式定义;查看响应中的错误字段与原因。
|
||||
- 业务规则失败:确认业务状态是否允许当前操作(如仅草稿或已驳回状态可更新);检查唯一性约束冲突(如工号、指标编码)。
|
||||
- 数据库约束失败:检查 CheckConstraint 与索引是否满足;确认外键关系是否正确。
|
||||
- 异常处理:查看全局异常处理器的日志输出,定位具体错误位置与堆栈信息。
|
||||
|
||||
**章节来源**
|
||||
- [backend/app/main.py](file://backend/app/main.py#L58-L74)
|
||||
- [backend/app/api/v1/staff.py](file://backend/app/api/v1/staff.py#L75-L78)
|
||||
- [backend/app/models/models.py](file://backend/app/models/models.py#L143-L146)
|
||||
|
||||
## 结论
|
||||
本系统通过“Pydantic 模式验证 + SQLAlchemy 数据库约束 + 服务层业务规则”的三层验证机制,确保了数据在进入业务流程前后的完整性与一致性。API 层负责输入验证与业务规则检查,服务层负责复杂业务逻辑与数据一致性,模型层负责数据结构与约束定义。配合统一的异常处理与日志记录,系统在保证功能正确的同时,也具备良好的可维护性与可扩展性。未来可在 Pydantic 中引入自定义验证器与复杂字段解析,在模型层增加更多数据库约束,并在服务层扩展业务规则检查点,进一步完善验证体系。
|
||||
Reference in New Issue
Block a user