正在为类依赖项分配属性
本文关键字:分配 属性 依赖 | 更新日期: 2023-09-27 18:28:52
假设我有一个类,它将IFileLogger作为构造函数参数。
public MyClass : IClass
{
private IFileLogger Logger;
public MyClass(IFileLogger Logger)
{
this.Logger = Logger;
}
}
在该类中的某个位置,它称为Logger.Write("Data");
IFileLogger的属性为DirectoryPath;
这需要设置,以便IFileLogger知道将文件写入何处。
这是怎么设置的?
我的想法是在类上设置一个属性,然后在构造函数中设置类似IFileLogger.DirectoryPath=this的属性。目录路径。
不过,这似乎是错误的,因为IClass需要包含属性,并且最终会创建一个只在底层需要的属性链。
你能帮助那些看不见树木的人吗?您还会编写测试以及如何确定IFileLogger的DirectoryPath已填充?
我可以建议你的界面设计是这里的问题,你的问题是气味的指示吗?
IFileLogger
表示您的类所依赖的接口。因此,查看该接口,我们可以看到有一个Write
方法。问题是,MyClass
并不真正关心日志记录是如何发生的,只是它符合接口。话虽如此,MyClass
需要知道目录位置才能告诉IFileLogger
如何完成它的工作的想法告诉你责任错了。
代码需要什么IFileLogger
?日志记录,对吧?让我们对代码进行一些重构,并根据客户端MyClass
的需求实现接口。他不在乎日志记录是如何发生的,只在乎日志记录会发生。
将接口重命名为ILogger
。
public MyClass : IClass
{
private ILogger Logger;
public MyClass(ILogger Logger)
{
this.Logger = Logger;
}
}
现在,这个类中的任何地方都没有对"File"的引用,这使得目录设置不属于这里变得更加明显。它属于哪里?可能在FileLogger
本身。
使用依赖注入会给你留下这样的东西:
main() {
// Poor man's DI, no frameworks here
var logger = new FileLogger("some/directory");
var instance = new MyClass(logger);
return instance.DoSomethingUsefulThatEventuallyGetsLogged();
}
希望能有所帮助!
Brandon
通常,我会说,一旦构建好对象,您的对象就应该可以使用了,而必须调用其他方法/属性才能准备好它只是令人困惑。因此,在将Logger传递到MyClass之前,它应该已经设置了DirectoryPath属性。例如:
SomeInitialisationMethod
()
{
// or use IOC "factory" to create necessary concrete version.
IFileLogger logger = new LoggerVariant("path");
// MyClass can now use the ready to use logger. If we need to set the DirectoryPath, we can do it on this calling stack through the logger.
MyClass myClass = new MyClass(logger);
如何以及在哪里实例化IFileLogger,听起来是设置其属性的地方。
builder.RegisterType<FileLogger>().WithParameter(new NamedParameter("directoryPath", @"c:'temp")).As<IFileLogger>();
使用此配置,无论何时使用该生成器解析IFileLogger,它都将使用"c:''Temp"作为directoryPath。