127 lines
4.6 KiB
Markdown
127 lines
4.6 KiB
Markdown
# 数据模型(Model)
|
||
|
||
数据模型是模块开发的第一步,用于定义数据库表结构。项目使用 `SQLAlchemy ORM`,模型类通过继承基类自动获得通用字段和方法。
|
||
|
||
## 文件位置
|
||
|
||
```
|
||
src/modules/system/position/models.py
|
||
```
|
||
|
||
## 完整代码
|
||
|
||
```python
|
||
from sqlalchemy import Column, String, Integer, text
|
||
|
||
from src.common.base_db import BaseDB
|
||
from src.common.base_model import BaseModel
|
||
from config.database import DB_PREFIX
|
||
|
||
|
||
class Position(BaseModel, BaseDB):
|
||
"""岗位模型类"""
|
||
# 表名配置
|
||
__tablename__ = DB_PREFIX + "position"
|
||
__table_comment__ = "岗位表"
|
||
|
||
# 业务字段定义
|
||
# 岗位名称
|
||
name = Column(String(255), nullable=False, index=True, comment="岗位名称")
|
||
# 岗位状态:1-在用 2-停用
|
||
status = Column(Integer, default=0, server_default=text('0'), index=True, comment="岗位状态:1-在用 2-停用")
|
||
# 岗位排序
|
||
sort = Column(Integer, default=0, server_default=text('0'), comment="岗位排序")
|
||
|
||
def __repr__(self):
|
||
"""返回岗位名称作为字符串表示"""
|
||
return '岗位:{}'.format(self.name)
|
||
```
|
||
|
||
## 代码解析
|
||
|
||
### 基类继承
|
||
|
||
```python
|
||
class Position(BaseModel, BaseDB):
|
||
```
|
||
|
||
| 基类 | 来源 | 提供能力 |
|
||
|:----|:----|:----|
|
||
| `BaseModel` | `src/common/base_model.py` | 通用字段:id、create_user、create_time、update_user、update_time、is_delete |
|
||
| `BaseDB` | `src/common/base_db.py` | `save()` 持久化方法、`delete()` 删除方法、`to_dict()` 序列化方法 |
|
||
|
||
### 表名配置
|
||
|
||
```python
|
||
__tablename__ = DB_PREFIX + "position"
|
||
```
|
||
|
||
`DB_PREFIX` 从 `.env` 读取(默认 `flask_`),最终表名为 `flask_position`。所有业务表都使用此前缀,便于区分框架表与业务表。
|
||
|
||
### 字段定义
|
||
|
||
```python
|
||
name = Column(String(255), nullable=False, index=True, comment="岗位名称")
|
||
```
|
||
|
||
| 参数 | 说明 |
|
||
|:----|:----|
|
||
| `String(255)` | 字段类型,VARCHAR(255) |
|
||
| `nullable=False` | 非空约束 |
|
||
| `index=True` | 创建索引,加速查询 |
|
||
| `comment` | 字段注释,同步到数据库 |
|
||
|
||
```python
|
||
status = Column(Integer, default=0, server_default=text('0'), index=True, comment="岗位状态:1-在用 2-停用")
|
||
```
|
||
|
||
`default=0` 是 Python 端默认值,`server_default=text('0')` 是数据库端默认值。两者都设置可确保无论通过 ORM 还是直接 SQL 插入,都能正确赋默认值。
|
||
|
||
### 枚举值约定
|
||
|
||
项目中状态字段统一使用整数枚举:
|
||
|
||
| 值 | 含义 |
|
||
|:----|:----|
|
||
| 1 | 启用 / 在用 |
|
||
| 2 | 停用 / 禁用 |
|
||
|
||
软删除字段 `is_delete` 由基类提供:`0` = 正常,`1` = 已删除。
|
||
|
||
## 数据表 DDL(参考)
|
||
|
||
模型定义对应的 MySQL 建表语句:
|
||
|
||
```sql
|
||
CREATE TABLE `flask_position` (
|
||
`name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL COMMENT '岗位名称',
|
||
`status` int DEFAULT '0' COMMENT '岗位状态:1-在用 2-停用',
|
||
`sort` int DEFAULT '0' COMMENT '岗位排序',
|
||
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
|
||
`create_user` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '创建人',
|
||
`create_time` datetime DEFAULT (now()) COMMENT '创建时间',
|
||
`update_user` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '更新人',
|
||
`update_time` datetime DEFAULT (now()) COMMENT '更新时间',
|
||
`is_delete` int DEFAULT '0' COMMENT '删除标识:0-正常 1-已删除',
|
||
PRIMARY KEY (`id`) USING BTREE,
|
||
KEY `idx_flask_position_name` (`name`) USING BTREE,
|
||
KEY `idx_flask_position_status` (`status`) USING BTREE,
|
||
KEY `idx_flask_position_is_delete` (`is_delete`) USING BTREE
|
||
) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC COMMENT='岗位表';
|
||
```
|
||
|
||
:::tip 温馨提示
|
||
实际开发中不需要手写 DDL。模型定义完成后,框架会通过 `Base.metadata.create_all()` 自动建表,或通过 `flask db migrate` 生成迁移脚本。
|
||
:::
|
||
|
||
## 开发要点
|
||
|
||
1. **业务字段仅定义差异部分**:通用字段(id、时间、软删除等)由基类自动提供
|
||
2. **表名必须加 `DB_PREFIX` 前缀**:保持命名一致性
|
||
3. **合理使用索引**:查询频繁的字段(如 name、status)设置 `index=True`
|
||
4. **同时设置 `default` 和 `server_default`**:确保 ORM 和直 SQL 两种场景都能正确赋默认值
|
||
|
||
## 总结
|
||
|
||
数据模型继承 `BaseModel`(公共字段)和 `BaseDB`(save/delete 方法),表名必须加 `DB_PREFIX` 前缀。查询频繁的字段设置索引,同时设置 `default` 和 `server_default` 确保 ORM 和直 SQL 两种场景都能正确赋默认值。
|