假设我有一个类,它将IFileLogger作为构造函数参数。
public MyClass : IClass
{
private IFileLogger Logger;
public MyClass(IFileLogger Logger)
{
this.Logger = Logger;
}
}
在该课程的某个地方,它会调用Logger.Write("Data");
IFileLogger具有DirectoryPath属性;
这需要设置,以便IFileLogger知道将文件写入的位置。
如何设定?
我的想法是在类上设置一个属性,然后在构造函数中有类似IFileLogger.DirectoryPath = this.DirectoryPath。
这似乎是错误的,因为IClass需要在其中包含属性,并且最终会创建仅在底层需要的属性链。
你能帮助那些看不见树木的人吗?您也会编写测试以及如何确定IFileLogger是否填充了DirectoryPath?
答案 0 :(得分:0)
如何以及在何处实例化IFileLogger,它听起来是设置其属性的地方。
builder.RegisterType<FileLogger>().WithParameter(new NamedParameter("directoryPath", @"c:\temp")).As<IFileLogger>();
使用此配置,只要您使用该构建器解析IFileLogger,它就会使用“c:\ Temp”作为directoryPath。
答案 1 :(得分:0)
一般来说,我会说你的对象应该在构造之后就可以使用了,并且必须调用其他方法/属性才能让它准备就绪,这简直令人困惑。因此Logger在将其传递给MyClass之前应该已经设置了DirectoryPath属性。 E.g:
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);
答案 2 :(得分:0)
我可能会建议你的界面设计是问题,你的问题是气味的指示吗?
IFileLogger
代表您的课程所依赖的界面。因此,查看界面,我们看到有Write
方法。问题是,MyClass
并不关心日志记录是如何发生的,只是它符合接口。话虽如此,MyClass
需要知道目录位置才能告诉IFileLogger
如何做到这一点的想法告诉你责任是错误的。
代码需要什么IFileLogger
?记录,对吧?让我们稍微重构代码并实现满足客户端需求的接口MyClass
。他并不关心 日志记录是如何发生的,只是将发生。
将界面重命名为ILogger
。
public MyClass : IClass
{
private ILogger Logger;
public MyClass(ILogger Logger)
{
this.Logger = Logger;
}
}
现在在这个类的任何地方都没有引用“文件”,这使得目录设置不属于此处更加明显。它属于哪里?可能在FileLogger
本身。
使用依赖注入会给你带来类似的东西:
main() {
// Poor man's DI, no frameworks here
var logger = new FileLogger("some/directory");
var instance = new MyClass(logger);
return instance.DoSomethingUsefulThatEventuallyGetsLogged();
}
希望有所帮助!
布兰登