简体   繁体   English

如何配置对象并覆盖该配置

[英]How to configure an object and override that configuration

I have the following interfaces and classes: 我有以下接口和类:

public interface ILoggingService { ... }
public class LoggingService {
    public LoggingService(ILoggingRepository loggingRepository) { ... }
    ...
}

public interface ILoggingRepository { ... }
public class DatabaseLoggingRepository {
    public DatabaseLoggingRepository(string ConnectionString) { ... }
    ...
}
public class FileLoggingRepository {
    public FileLoggingRepository(string LogFilePath) { ... }
    ...
}

I'm refactoring my software to use Unity IoC framework and am looking for a way to pass the specific configuration to each ILoggingRepository implementation. 我正在重构我的软件以使用Unity IoC框架,并且正在寻找一种方法将特定配置传递给每个ILoggingRepository实现。

I think that the best way would be to change DatabaseLoggingRepository's and FileLoggingRepository's constructors to have no parameters at all and have them configured by some configuration file. 我认为最好的方法是将DatabaseLoggingRepository和FileLoggingRepository的构造函数更改为根本没有参数,并让它们由某个配置文件配置。 However, because of my acceptance tests I would need a easy way to override these settings while running my tests. 但是,由于我的验收测试,我需要一种简单的方法来在运行测试时覆盖这些设置。

Am I on the right track and if I am, which configuration files should I use? 我是在正确的轨道上,如果我,我应该使用哪些配置文件? Alternative ways are welcome as well. 也欢迎其他方式。

What we've decided to do is create a class, in your case it would be LoggingConfiguration , and have that passed to the constructo of the repository. 我们决定创建一个类,在您的情况下它将是LoggingConfiguration ,并将其传递给存储库的constructo。 If you resolve using Unity it will instantiate this class using Activator , wuthout having to register it. 如果您使用Unity解析它将使用Activator实例化此类,wuthout必须注册它。 In your tests however, you just greate a new instance of a derived configuration class, providing different values. 但是,在测试中,您只需更新派生配置类的新实例,从而提供不同的值。

Does it makes sense? 这有道理吗? Should I clarify more? 我应该澄清一下吗?

Update : I've decided to provide some additional clarification. 更新 :我决定提供一些额外的说明。 So, you already have two implementations, and now you want each configuration to query for its proper configuration setting. 因此,您已经有两个实现,现在您希望每个配置都查询其正确的配置设置。

I would extend the ILoggingRepository 's constructor to look like this: 我会将ILoggingRepository的构造函数扩展为如下所示:

   public ILoggingRepository(ILoggingConfigurationProvider confProvider);

You can then create one implementation for your normal operation which has two properties: 然后,您可以为正常操作创建一个具有两个属性的实现:

public LoggingConfigurationProvider : ILoggingConfigurationProvider {
 public LoggingConfigurationProvider() {
   // load both values from configuration file
 }

 public string LogPath { get; set; }
 public string ConnectionString { get; set; }
}

When you instantiate your class via normal IoC operation this will get resolved by the container and you'll configuration options will get loaded from the conf file. 当您通过正常的IoC操作实例化您的类时,这将由容器解决,您将从conf文件加载配置选项。 When you however want to do Unit tests you: 但是当你想要进行单元测试时:

1) Create a new "Mock" implementation 1)创建一个新的“模拟”实现

public class MockLoggingConfigurationProvider : ILoggingConfigurationProvider  {
   public MockLoggingConfigurationProvider() {
      // set both values to a test value
   }

   public string LogPath { get; set; }
   public string ConnectionString { get; set; }
}

Now you can either create the repository using a constructor: 现在,您可以使用构造函数创建存储库:

new LoggingRepository(new MockLoggingConfigurationProvider());

or if you want the whole IoC mechanism to be used, you simply (when setting up the container) register this implementation of the interface. 或者如果您希望使用整个IoC机制,您只需(在设置容器时)注册该接口的实现。 Because the unit tests are separate, you don't share the registrations right? 因为单元测试是分开的,所以你不共享注册吗? So that should give you what you need, the ability to change this settings depending on weather they are being executed as a unit test or not. 因此,应该为您提供所需的功能,可以根据天气作为单元测试执行来更改此设置。

In real life, I wouldn't even bother with this, and just create a mock logging repository and have it write somewhere else. 在现实生活中,我甚至不愿意这样做,只需创建一个模拟日志存储库并将其写入其他地方。 Unless you want to test the repository to a test database/file. 除非您要将存储库测试到测试数据库/文件。 In which case I'd do as specified. 在这种情况下,我会按照规定做。

Hope it helps. 希望能帮助到你。

As a design suggestion does not force IoC to deal with configuration stuff. 由于设计建议不强制IoC处理配置内容。 Each logger should manage the configuration the way they prefer in its implementation. 每个记录器应该在实现时按照自己喜欢的方式管理配置。 IoC should just inject the logger. IoC应该只注入记录器。 For the unit/integration test, in both case you should e able to provide a configuration for the logger, for example using log4net I'm used to configure the logging subsystem in the Startup of the test by the api, and I create an appender that write just everithing on the console. 对于单元/集成测试,在这两种情况下,您都应该能够为记录器提供配置,例如使用log4net我用于在api的测试启动中配置记录子系统,并且我创建了一个appender在控制台上写的只是一个人。 You can't Insolate configuration by IoC since each possible logging system does not necessary share a contract for the Configuration part. 您无法通过IoC进行Insolate配置,因为每个可能的日志记录系统都不需要共享配置部分的合同。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 .net中如何覆盖列表配置 - How to override list configuration in .net 如何配置自定义配置对象 - How to configure custom configuration objects 如何使用环境变量覆盖 blazor 客户端配置? - How to override blazor client configuration with environment variables? .Net配置-如何覆盖映射的配置文件中的设置和自定义部分? - .Net configuration - How to override settings and custom sections in a mapped configuration file? 如何配置工厂生成对象? - How to configure the factory to generate the object? 使用 UseSetting 覆盖配置 - Override configuration with UseSetting 与Entlib5一起使用共享配置时,如何覆盖日志记录配置? - How to override logging configuration when using shared config with Entlib5? 如何在 .NET 核心 API 中使用 Autofac 为配置文件配置 DI? - How to configure DI for a configuration file with Autofac in .NET core API? 如何在 Autofac json 配置文件中配置 DbContext - How do I configure the DbContext in an Autofac json configuration file 如何配置运行配置以在 JetBrains Rider 中执行 Main function - How to configure Run Configuration to execute Main function in JetBrains Rider
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM