You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Sea-ORM MockDatabase中正确Mock COUNT查询结果用于测试?

问题

我正在测试一个基于Sea-ORM的函数,该函数通过COUNT查询检查数据库中是否存在指定space,但测试始终失败。

仓库代码

pub async fn space_check_exist(db: &DatabaseConnection, space_id: &str) -> Result<bool, DbErr> {
    let count = Space::find()
        .filter(space::Column::SpaceId.eq(space_id))
        .count(db)
        .await?;

    Ok(count > 0)
}

测试代码

#[tokio::test]
async fn test_space_check_exist_when_space_exists() {
    let db = MockDatabase::new(DatabaseBackend::Postgres)
        .append_query_results([vec![space::Model {
            id: 1,
            space_id: "test-space-id".to_owned(),
            space_status_id: 1,
            space_config: Json::Null,
            created_at: chrono::Utc::now().naive_utc(),
            updated_at: chrono::Utc::now().naive_utc(),
            deleted_at: None,
        } as space::Model] as Vec<space::Model>])
        .into_connection();

    // Run test
    let result = SpaceRepository::space_check_exist(&db, "test-space-id").await;

    // Verify result
    // assert!(result.is_ok());
    assert!(result.unwrap());
}

测试失败情况

  • 执行assert!(result.is_ok())时,测试panic并提示断言失败;
  • 执行assert!(result.unwrap())时,panic提示解码"num_items"遇到空值。

尝试过使用完整的space::Model、不同配置的MockRow来Mock COUNT查询结果,但都无法成功。如何在Sea-ORM中正确Mock COUNT查询结果?

环境

  • Rust 1.83.0
  • sea-orm 1.1.4

解决方法

问题核心是Mock的数据类型不匹配:COUNT查询返回的是单一数值(对应SQL的COUNT(*)结果),而你Mock的是完整的space::Model实例,Sea-ORM无法将Model映射到COUNT需要的num_items字段,因此出现解码空值错误。

正确做法是直接Mock COUNT查询的返回值,即包含num_items字段的MockRow,而非完整Model。

修改后的测试代码

#[tokio::test]
async fn test_space_check_exist_when_space_exists() {
    // Mock COUNT查询返回1(表示存在匹配记录)
    let db = MockDatabase::new(DatabaseBackend::Postgres)
        .append_query_results([vec![MockRow::new([("num_items", 1_i64.into())])]])
        .into_connection();

    let result = SpaceRepository::space_check_exist(&db, "test-space-id").await;
    
    // 验证结果:成功且返回true
    assert!(result.is_ok());
    assert!(result.unwrap());
}

// 补充:测试space不存在的场景
#[tokio::test]
async fn test_space_check_exist_when_space_not_exists() {
    // Mock COUNT查询返回0(表示无匹配记录)
    let db = MockDatabase::new(DatabaseBackend::Postgres)
        .append_query_results([vec![MockRow::new([("num_items", 0_i64.into())])]])
        .into_connection();

    let result = SpaceRepository::space_check_exist(&db, "non-existent-id").await;
    
    assert!(result.is_ok());
    assert!(!result.unwrap());
}

关键说明

  • Sea-ORM的count方法执行SQL后,会返回名为num_items的列(Postgres环境下),因此MockRow必须包含该字段;
  • COUNT返回值为64位整数,需用1_i64.into()转换为Sea-ORM的Value类型;
  • 若需Mock多个查询,需按代码中查询执行顺序依次调用append_query_results。

内容的提问来源于stack exchange,提问作者localhost80808

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.14 07:53:25