App.config for Xunit

本文关键字:Xunit for config App | 更新日期: 2023-09-27 18:35:09

我正在为一些依赖于某些配置设置的帮助程序类编写一些xUnit测试,这些帮助程序类通常存储在正在执行项目的App.config或Web.config中。

配置如下所示:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <appSettings>
    <add key="FileNamePattern" value="''d{8}_''w{4:20}'.png"/>
    <!-- and the likes -->
  </appSettings>
</configuration>

我正在使用GUI运行器(xunit.gui.clr4.exe)和xUnit控制台运行器(在Jenkins CI服务器上)运行xUnit 1.9。目前,我可以通过手动设置 xunit.gui.clr4.exe.config 和 xunit.console.exe.config 文件将这些配置值"注入"到测试环境中);但是,这很乏味且容易出错。

我也可以在夹具中模拟这些配置设置。但是在 10 个不同的文件中使用相同的夹具是相当重复的。

是否有更好的方法来使用 xUnit 模拟这些配置设置,例如为测试项目提供 App.config 文件?

App.config for Xunit

如果你的代码假设它们在app.config中,那么 xUnit.net 支持通过提供一个来将它们连接在那里(通常当测试在 DLL 文件中时,这意味着你在项目输出中得到一个AssemblyName.dll.config文件,如果它在加载时存在,则运行器将作为设置加载

)。

显然,首先使用 DI 原则删除此类依赖项没有害处,但我想说的是,在你真正先对其进行测试之前,不要弄乱代码。

要保持干燥,请将 app.config 放在中心位置并将其添加为链接(通过对话框中"打开"按钮上的箭头)。(是的,有很多不喜欢的地方 - 只有在你觉得这是最不邪恶的方法时才使用。


需要注意的一件事是,除非您要求重新加载程序集,否则不会在 GUI 运行器中重新加载更改。

从更复杂的项目和团队合作的角度来看,我建议:

  1. xUnit项目的单独.config文件(它利用独立的配置和日志记录来运行测试)
  2. 单独为 xUnit 项目设置依赖注入.config 读取

我们的团队正在使用这种xUnit init和dispose模式:

    public class MyTest : IDisposable
    {
        public IServiceProvider Services { get; private set; }
        public MyProjectOptions Options { get; private set; }
        public Logger Logger { get; private set; }
        private void Configure()
        {
            // appsettings.workspace.json for custom developer configuration
            var configuration = new ConfigurationBuilder()
                .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("appsettings.json")
                .AddJsonFile("appsettings.workspace.json", optional: true)
                .Build();
            Logger = new LoggerConfiguration()
                .MinimumLevel.Debug()
                .WriteTo.LiterateConsole()
                .WriteTo.RollingFile("logs/{Date}-log.txt")
                .CreateLogger();
            Options = configuration.GetSection("MyProject").Get<MyProjectOptions>();
            var services = new ServiceCollection();
            services.AddSingleton<ILogger>(s => Logger);
            // other DI logic and initializations ...
            //services.AddTransient(x => ...);
            Services = services.BuildServiceProvider();
        }
        public MyTest()
        {
            Configure();
            // ... initialize data in the test database ...
            var data = Services.GetService<TestDataService>();
            data.Clean();
            data.SeedData();
        }
        public void Dispose()
        {
            // ... clean-up data in the test database ...
            var data = Services.GetService<TestDataService>();
            data.Clean();
        }
    }

我的解决方案是将配置文件命名为testhost.dll.config,将其添加到解决方案中,并将其Copy to Output Directory设置设置为 Copy always

它必须被命名为testhost.dll.config因为这就是调用我的测试项目的xUnit组件的命名方式。可以按如下方式确定:

string invoker = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None).FilePath;

对于我的设置,invoker结果是testhost.dll.