name: rust-db-contracts description: > Rust + SeaORM 数据库显式契约规范。当项目涉及 Rust + SeaORM 数据库开发时自动激活。 核心:Entity 文件完全表达数据表,消灭隐式契约。
一句话:Entity 文件就是数据表的完全表达。 打开一个 entity 文件,不需要连数据库、不需要看 DDL,就能知道这张表的一切。
| 数据表特性 | Rust 写法 | 说明 |
|---|---|---|
| NOT NULL | pub name: String |
不写 Option = NOT NULL,SeaORM 建表时自动加约束 |
| 可为 NULL | pub name: Option<String> |
编译器强制处理 None |
| 枚举字段 | pub status: MyEnum |
用 Rust enum + DeriveActiveEnum。禁止用 String |
| JSON 字段 | pub config: MyStruct |
用强类型 struct + FromJsonQueryResult。禁止用 String 或 serde_json::Value(结构不固定时除外) |
| 时间字段 | pub created_at: DateTimeUtc |
禁止用 NaiveDateTime,统一 UTC |
| 默认值 | #[sea_orm(default_value = "xxx")] |
注解标注,SeaORM 建表时自动加 DEFAULT |
| 主键 | #[sea_orm(primary_key)] |
|
| 唯一约束 | #[sea_orm(unique)] |
|
| 索引 | #[sea_orm(indexed)] |
有状态流转的枚举,必须实现 can_transition_to() 方法,状态变更前必须调用。
impl OrderStatus {
pub fn can_transition_to(&self, next: &OrderStatus) -> bool {
matches!((self, next),
(OrderStatus::Draft, OrderStatus::Active)
| (OrderStatus::Active, OrderStatus::Archived)
)
}
}
member_level.max_borrows())db.transaction::<_, ResultType, ErrType>(|txn| {
Box::pin(async move {
// 所有操作共享 txn,出错自动 rollback
Ok(result)
})
}).await?;
使用软删除(is_deleted: bool)的表,查询活跃记录时必须带 .filter(Column::IsDeleted.eq(false))。除非明确需要查全量(注释说明原因)。
//! doc comment:业务规则、状态流转、软删除约定、关联关系等/// 注释:业务含义,不只是字段名的复述使用 SeaORM 2.0 Entity First,entity 就是数据库 schema 的唯一事实源:
let db = Database::connect(db_url).await?;
db.get_schema_registry("my_crate::entity::*").sync(db).await?;
#[sea_orm(renamed_from = "old_name")] 自动 RENAME以下不是强制要求,根据项目规模和需要决定:
Relation enum):需要关联查询(JOIN/预加载)时添加impl Model { fn new_xxx() }):有动态默认值(如"可借数量 = 总数量")时添加,让创建逻辑集中在 entity 文件impl Entity { async fn find_xxx() }):同一段查询逻辑重复使用时提取String 存枚举值String 或 serde_json::Value 存结构化 JSONNaiveDateTimecan_transition_to()小葱技能7w4.net有更新,你可以访问看下。
can_transition_to() 方法参考 references/ENTITY_EXAMPLE.md 获取完整示例。
references/check_db_contracts.sh 可集成到 CI,自动检查以上规则。
# 用法
./check_db_contracts.sh [src_dir] # 默认 ./src
# 集成到 CI
cargo build && ./check_db_contracts.sh
检测项:
- 是否引入了非 SeaORM 数据库库(rusqlite/sqlx/diesel 等)
- 是否有裸 SQL 操作(execute_unprepared / 硬编码 SQL 语句)
- col_expr 中是否用了字符串字面量(应用 .set(ActiveModel) 替代)
- Entity 文件中是否用了 serde_json::Value 或 NaiveDateTime
- 状态变更是否有 can_transition_to() 检查
- 软删除表查询是否过滤了 is_deleted
- Entity 文件是否有文件级 doc comment 和字段注释
错误(❌)会导致脚本返回非零退出码(CI 失败),警告(⚠)不阻断。
这个 Skill 质量不错,文档清晰规范,示例完整,配套的自动检测工具也很实用。它为 Rust 数据库开发提供了明确的质量标准,能帮助避免常见错误。虽然内容专业、适用范围有一定局限,但对于需要这类规范的项目来说,是一份值得信赖的参考资源。