NLog DatabaseTarget安装无法正常工作

时间:2015-12-16 13:54:08

标签: c# asp.net-core nlog

使用NLog 4.2.2和asp net 5.我的所有NLog配置都在代码上。我需要部署我的项目,并希望确保创建适当的SqlServer表和StoredProcedure。我正在使用这样的DatabaseTarget.Install()方法:

dbTarget.InstallDdlCommands.Clear();
dbTarget.InstallDdlCommands.Add(new DatabaseCommandInfo
{
    ConnectionString = connectionString,
    CommandType = System.Data.CommandType.Text,
    IgnoreFailures = false,
    Text = $@"CREATE TABLE [dbo].[{TableName}] (
           [ID] [int] IDENTITY(1,1) NOT NULL,
           [MachineName] [nvarchar](200) NULL,
           [SiteName] [nvarchar](200) NOT NULL,
           [Logged] [datetime] NOT NULL,
           [Level] [varchar](5) NOT NULL,
           [UserName] [nvarchar](200) NULL,
           [Message] [nvarchar](max) NOT NULL,
           [Logger] [nvarchar](300) NULL,
           [Properties] [nvarchar](max) NULL,
           [ServerName] [nvarchar](200) NULL,
           [Port] [nvarchar](100) NULL,
           [Url] [nvarchar](2000) NULL,
           [Https] [bit] NULL,
           [ServerAddress] [nvarchar](100) NULL,
           [RemoteAddress] [nvarchar](100) NULL,
           [Callsite] [nvarchar](300) NULL,
           [Exception] [nvarchar](max) NULL,
         CONSTRAINT [PK_dbo.Log] PRIMARY KEY CLUSTERED ([ID] ASC) 
           WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
        ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY];"
});

dbTarget.InstallDdlCommands.Add(new DatabaseCommandInfo
{
    ConnectionString = connectionString,
    CommandType = System.Data.CommandType.Text,
    IgnoreFailures = false,
    Text = $@"CREATE PROCEDURE [dbo].[{ProcName}] (
              @machineName nvarchar(200),
              @siteName nvarchar(200),
              @logged datetime,
              @level varchar(5),
              @userName nvarchar(200),
              @message nvarchar(max),
              @logger nvarchar(300),
              @properties nvarchar(max),
              @serverName nvarchar(200),
              @port nvarchar(100),
              @url nvarchar(2000),
              @https bit,
              @serverAddress nvarchar(100),
              @remoteAddress nvarchar(100),
              @callSite nvarchar(300),
              @exception nvarchar(max)
            ) AS
            BEGIN
              INSERT INTO [dbo].[{TableName}] (
                [MachineName],
                [SiteName],
                [Logged],
                [Level],
                [UserName],
                [Message],
                [Logger],
                [Properties],
                [ServerName],
                [Port],
                [Url],
                [Https],
                [ServerAddress],
                [RemoteAddress],
                [CallSite],
                [Exception]
              ) VALUES (
                @machineName,
                @siteName,
                @logged,
                @level,
                @userName,
                @message,
                @logger,
                @properties,
                @serverName,
                @port,
                @url,
                @https,
                @serverAddress,
                @remoteAddress,
                @callSite,
                @exception
              );
            END"
});

using (var context = new InstallationContext())
{
    if (dbTarget.IsInstalled(context) != true)
        dbTarget.Install(context);
}

但是当我运行我的代码时,我得到了这个异常System.ArgumentNullException | Value cannot be null. |Parameter name: type

我已经看到了question,我认为我正在做他们所说的但仍然不适合我。我知道其余的代码是好的,因为一旦我手动创建Table和StoredProcedure,DB日志就可以了。

1 个答案:

答案 0 :(得分:1)

过了一会儿,我在github上打开了一个issue,我从那里得到了答案。事实证明,截至目前,当您以编程方式创建配置文件(就像我一样)时,您必须手动调用configuration.Install(installationContext)以便实际初始化不同的目标,作为副作用它还将运行拥有它的目标的Install方法。所以上面的代码需要做的就是

 // Target configuration as is (except for the installation part)
 config.AddTarget(dbTarget);

 using(var context = new InstallationContext())
 {
     config.Install(context);
 }

如果有多个目标虽然我认为应该在所有目标(或至少大部分目标)添加后调用config.Install(context),因为它初始化所有注册目标并运行Install就可以了。