NLog自定义目标运行时依赖项

时间:2018-08-07 15:07:09

标签: c# nlog

问题: 我的数据库逻辑放在一些大的DataBaseObject中。它包含方法,连接字符串以及该逻辑层所需的一切。如何在运行时将其放入NLog自定义目标中?

这几乎可以正常工作(请参见备注):

using NLog;
using NLog.Config;
using NLog.Targets;
using Data.Base.Object.Namespace;

namespace MyNamespace 
{ 
    [Target("DatabaseLog")] 
    public sealed class DatabaseLogTarget: TargetWithLayout 
    { 
        private IDataBaseObject _db;

        public DatabaseLogTarget()
        {

        }

        [RequiredParameter] 
        public string ConnectionString { get; set; }

        protected override void Write(LogEventInfo logEvent) 
        { 
            Save(logEvent); 
        } 

        private void Save(LogEventInfo logEvent) 
        { 
            if (_db == null) { _db = new DataBaseObject(ConnectionString); }
            _db.Log();
        } 
    } 
}

这不起作用,但是我需要什么:

using NLog;
using NLog.Config;
using NLog.Targets;
using Data.Base.Object.Namespace;

namespace MyNamespace 
{ 
    [Target("DatabaseLog")] 
    public sealed class DatabaseLogTarget: TargetWithLayout 
    { 
        private IDataBaseObject _db;

        public DatabaseLogTarget(IDataBaseObject db)
        {
            _db = db;
        } 

        protected override void Write(LogEventInfo logEvent) 
        { 
            Save(logEvent); 
        } 

        private void Save(LogEventInfo logEvent) 
        {           
            _db.Log();
        } 
    } 
}

备注:

  1. 我不想使用标准的DataBase目标,因为在这种情况下,我需要支持两个配置,并且数据库工作逻辑将位于不同的位置。
  2. 当前版本存在瓶颈:
if (_db == null) { _db = new DataBaseObject(ConnectionString); }

...因为DataBaseObject非常大。

  1. 我阅读了一些有关依赖注入的信息,但是这种技术导致了某些程序包的依赖。这意味着有更多地方可以分解所有东西。

1 个答案:

答案 0 :(得分:0)

您可以使用GlobalDiagnosticsContext存储IDataBaseObject并将其用于目标。

代码中的某处:

GlobalDiagnosticsContext.Set("key1", myDbObject);

并在目标中阅读它:

var myDbObject = GlobalDiagnosticsContext.GetObject("key1");

注意:如果需要有限的作用域,还可以使用MappedDiagnosticsContext(每个线程的作用域)或MappedDiagnosticsLogicalContext(每个线程的作用域,包括异步Tasks