x单位理论。测试之间的数据库有多清晰

问题描述 投票:0回答:2

我使用 xUnit [理论] 编写测试。我的问题是我运行第一个测试并通过,而第二个测试抛出异常 ---- Microsoft.Data.Sqlite.SqliteException :SQLite 错误 19:'UNIQUE 约束失败:CONTRAHENT.ID'。当我单独运行每个测试时,在测试资源管理器中它们都通过了。所以我假设数据库在第二次运行之前没有被清除/处置。

 public class TestDatabaseFixture
    {
        private const string ConnectionString = "DataSource=file::memory:?cache=shared";
        private static readonly object _lock = new();
        private static bool _databaseInitialized;

        public TestDatabaseFixture()
        {

            lock (_lock)
            {
                if (!_databaseInitialized)
                {
                    using (var context = CreateContext())
                    {
                        context.Database.EnsureDeleted();
                        context.Database.EnsureCreated();
                    }

                    _databaseInitialized = true;
                }
            }
        }

        public DbTrancheTest CreateContext(bool sensitiveDataLoggingEnabled = false)
            => new DbTrancheTest(
                new DbContextOptionsBuilder<DbTranche>()
                .EnableSensitiveDataLogging(sensitiveDataLoggingEnabled)
                .UseSqlite(ConnectionString)
                .Options);


    }

测试课

public class TrancheServiceTest : IClassFixture<TestDatabaseFixture>
    {
        private TestDatabaseFixture Fixture { get; }
        // private readonly ITestOutputHelper output;
        public TrancheServiceTest(TestDatabaseFixture fixture)
        {
            Fixture = fixture;
        }

            [Theory]
            [InlineData(TrancheStatus.created, true)] // passed
            [InlineData(TrancheStatus.accepted, false)] // failed
            [InlineData(TrancheStatus.chanaged, true)] // failed
            [InlineData(TrancheStatus.waitforconf, false)] // failed
            [InlineData(TrancheStatus.rejected, false)] //failed
           
            public void Should_Set_Can_Edit_Flag_For_User(TrancheStatus status, bool result)
            {
                // Arrange
                using var context = Fixture.CreateContext();
                context.Database.EnsureDeleted();
                context.Database.EnsureCreated();
    
              
                var orderRepository = new TrancheOrderRepository(context);
                var userRepo = new UserRepository(context);
                var contrahentRepository = new ContrahentRepository(context);
    
                contrahentRepository.Add(new CONTRAHENT { ID = 1, NAME = "Contrahent1" });
                contrahentRepository.Save();

                var trancheOrder = new TRANCHE_ORDER
                {
                    ID = 1,
                    ISSUE_DATE = DateTime.Parse("2023-02-01"),
                    LAST_UPDATE = DateTime.Parse("2023-02-01"),
                    STATUS = (short)status,
                    VOLUME = 0,
                    USER = "",
                };
                orderRepository.Add(trancheOrder);
                orderRepository.Save();
    
                userRepo.Add(new USER { ID = 1, CAN_MODIFY = 1, DESCRIPTION = "Test user", FK_CONTRAHENT_ID = 1, NAME = "User1", USER_ID = 123 });
                userRepo.Save();
    
                var service = new TrancheService(contrahentRepository, orderRepository, userRepo);
                DateTime dateFrom = DateTime.Parse("2023-01-01");
                DateTime dateTo = DateTime.Parse("2023-12-01");
    
                // Act
                var trancheList = service.GetTrancheList(dateFrom, dateTo, 123, true);
    
                // Assert
                Assert.Collection(trancheList,
                    e => Assert.Equal(result, e.CanEdit));
    
            }
}
c# xunit
2个回答
1
投票

就像@fildor所说,你每次都可以创建一个新的数据库。为此,您可以使用连接字符串,如下所示:

ConnectionString = "file:{0}?mode=memory";  

并像这样更新你的代码:

public TestDatabaseFixture()
    {

        lock (_lock)
        {
                using (var context = CreateContext())
                {
                    context.Database.EnsureDeleted();
                    context.Database.EnsureCreated();
                }
            }
        }
    }

public DbTrancheTest CreateContext(bool sensitiveDataLoggingEnabled = false)
        => new DbTrancheTest(
            new DbContextOptionsBuilder<DbTranche>()
            .EnableSensitiveDataLogging(sensitiveDataLoggingEnabled)
            .UseSqlite(string.Format(ConnectionString, DateTime.Now.Ticks))
            .Options);

0
投票

我最终在每个单独的测试中创建上下文,如下所示。所有测试均通过。

  using var context = new DbTrancheTest(
        new DbContextOptionsBuilder<DbTranche>()
        .EnableSensitiveDataLogging(false)
        .UseSqlite(string.Format("DataSource=file::memory:?{0}", Guid.NewGuid().ToString()))
        .Options);

    context.Database.EnsureDeleted();
    context.Database.EnsureCreated();
© www.soinside.com 2019 - 2024. All rights reserved.