C# 将依赖项(NLog)注入到动态加载的类型中

C# 将依赖项(NLog)注入到动态加载的类型中,c#,dependency-injection,dynamic,nlog,plugin-architecture,C#,Dependency Injection,Dynamic,Nlog,Plugin Architecture,我的解决方案中有一种插件架构。 有一个众所周知的文件夹,可以在其中放置插件。 插件实现了一个在宿主项目中共享的接口 最初我通过Assembly.LoadFrom(fi.FullName.GetTypes() 并通过(IPlugin)Activator.CreateInstance(type)实例化所需的类型 因此主机(主应用程序)可以执行插件程序集实现的适当代码。到目前为止,这一切都很好 但最近我尝试通过NLog实现应用程序日志记录,并在主机项目中配置了NLog,效果非常好 问题是我想在插件程序

我的解决方案中有一种插件架构。 有一个众所周知的文件夹,可以在其中放置插件。 插件实现了一个在宿主项目中共享的接口

最初我通过
Assembly.LoadFrom(fi.FullName.GetTypes()
并通过
(IPlugin)Activator.CreateInstance(type)实例化所需的类型

因此主机(主应用程序)可以执行插件程序集实现的适当代码。到目前为止,这一切都很好

但最近我尝试通过NLog实现应用程序日志记录,并在主机项目中配置了NLog,效果非常好

问题是我想在插件程序集中使用(已经配置的)记录器。 如果我只是引用NLog并通过
LogManager.GetCurrentClassLogger()使用它似乎没有配置集。它不会从插件程序集中登录到我在宿主项目中配置的文件

我想尝试将NLogger实例(在宿主项目中创建)注入到插件类型的属性中

这是可能的还是有更好的方法来完成这样的事情?
谢谢

看看Unity或Lightcore之类的依赖注入容器

它们是某种“组件注册存储”

在那里,您可以将组件注册到接口。然后,您的消费者只需要请求一个接口

接口组件的映射可以在配置文件或源代码中进行

因此,您可以毫不费力地更改映射

例如,当他们创建新实例时,您将complextypes作为ctor参数,如果这些组件已注册,他们可以进行自动查找,然后自动注入它们

一些可以帮助您的关键字是“ServiceLocator”“微核”“依赖注入”

组成部分:

  • 还有一种更以插件为中心的方法是

这应该有效-NLog配置也应该适用于加载的插件程序集。 问题可能与插件的加载方式有关。可能它们位于单独的域中(我不记得它是如何工作的),因此NLog无法访问主要应用程序的日志配置

在这种情况下,您可以尝试为插件程序集添加单独的nlog配置文件(阅读有关配置文件命名约定的nlog文档)

我不认为IOC容器会在动态加载插件的情况下帮助你-容器不会知道它们,因此你必须改变加载和配置插件的方式。imho使用IOC配置nlog不是一个好主意

如果前面的选项不起作用,您可以尝试更改app.config中的程序集探测路径,以便将您的插件加载到默认域中-然后NLog应该适用于这些插件(至少适用于我):



假设我将使用DI容器解析插件。插件本身需要一个logger实例(已在主机系统中配置,在何处记录文件等等)。这将如何与NLog一起工作?我可以按照已经配置的方式注入记录器吗?我不确定我是否理解您,但您也可以将活动实例注册到某些类型。例如,您创建了一个Loggerinstance,并将其注册为ILogAdapter。顺便说一句,当使用Di容器时,你应该看看CommonServiceLocator,这样你就可以在不更改代码的情况下更改Dic。如果IoC已经内置了支持,比如Ninject或Castle.Windsor的日志记录设施,那么使用IoC是个好主意。但是我假设作者在他的组件中已经具有NLog依赖性(他的插件已经在使用NLog进行日志记录)因此不需要外部注入NLog。需要的是单个NLog配置对应用程序及其插件都起作用。是的,这个问题不是IoC能解决的。正如你的回答所述,我也希望它能正常工作。我唯一不同意的是“imho使用IOC配置nlog不是一个好主意”,除非“配置”是指配置侦听器/输出等,而不是配置记录器类本身。IOC非常适合连接记录器类。正如您所评论的,这不是必要的,但可能会有所帮助。
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
  <probing privatePath="Plugins" />
</assemblyBinding>