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

使用TestContainers(.NET 8)时EF无法查询插入数据的问题排查

问题分析与解决方案

可能的原因及对应解决方法

1. EF上下文缓存未更新

EF Core的DbContext会自动缓存已查询的实体,而通过ExecuteSqlRawAsync执行的原生SQL操作不会主动同步更新上下文缓存。数据库里已经有插入的数据,但EF优先读取本地缓存,自然查不到新数据。

解决方式:

  • 执行完SQL脚本后,清空上下文缓存,强制EF从数据库重新查询:
await DbContext.Database.ExecuteSqlRawAsync(query, CancellationToken.None);
DbContext.ChangeTracker.Clear(); // 清空本地缓存
var fakeTable = await DbContext.FakeTable.SingleOrDefaultAsync(v => v.Id == Guid.Parse("B98FD396-66D4-45A4-9247-9D5B4DB851E2"));
  • 或者查询时跳过缓存,直接访问数据库:
var fakeTable = await DbContext.FakeTable.AsNoTracking().SingleOrDefaultAsync(v => v.Id == Guid.Parse("B98FD396-66D4-45A4-9247-9D5B4DB851E2"));

2. 事务未提交或隔离级别问题

如果测试中存在未完成的事务,或者EF的事务配置导致插入数据未被查询可见。虽然ExecuteSqlRawAsync默认自动提交,但如果上下文之前开启了事务且未结束,会影响数据的可见性。

解决方式:

  • 若手动开启了事务,确保执行脚本后提交:
using var transaction = await DbContext.Database.BeginTransactionAsync();
await DbContext.Database.ExecuteSqlRawAsync(query, CancellationToken.None);
await transaction.CommitAsync();
  • 每个测试用例使用全新的DbContext实例(比如在[Fact]前重新初始化上下文),避免上下文状态污染。

3. SQL脚本执行或实体映射问题

需确认ExecuteSqlRawAsync是否真的成功执行脚本,以及EF实体与数据库表的映射是否匹配:

  • 验证脚本执行的受影响行数,确认数据已插入:
var rowsAffected = await DbContext.Database.ExecuteSqlRawAsync(query, CancellationToken.None);
rowsAffected.Should().BeGreaterThan(0); // 确保有数据被插入
  • 检查FakeTable实体的映射配置,确保[Table]特性或FluentAPI指定的表名,与SQL脚本中的表名完全一致(注意SQL Server的大小写配置,若开启区分大小写会导致匹配失败)。

4. 连接字符串不一致

如果EF的DbContext使用的连接字符串,与你用ADO.NET测试时的连接字符串不同,会导致两者访问的不是同一个数据库实例。

解决方式:

  • 确认测试中DbContext的连接字符串,与ADO.NET测试时完全一致,均指向TestContainers启动的SQL Server实例。可以在测试中打印连接字符串进行核对。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.23 22:40:05