我正在尝试将我从应用程序收到的任何日志保存到我的数据库中的日志表中,到目前为止,没有任何内容被保存。我正在使用Log4net和AdoNetAppender将日志保存到SQL Server中的表中。此代码位于我的应用程序服务器端的Web API项目中。
我按如下方式设置日志:
1)在我的Web.Config中设置XML:
<log4net>
<appender name="AdoNetAppender" type="log4net.Appender.AdoNetAppender">
<bufferSize value="1" />
<connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=token" />
<connectionString value="data source=db;Initial Catalog=dbname;Trusted_Connection=True;" providerName="System.Data.SqlClient" />
<commandText value="dbo.procLogs_Insert" />
<commandType value="StoredProcedure" />
<parameter>
<parameterName value="@log_timestamp" />
<dbType value="DateTime" />
<layout type="log4net.Layout.RawTimeStampLayout" />
</parameter>
<parameter>
<parameterName value="@log_recordNum" />
<dbType value="Int32" />
<size value="32" />
<layout type="log4net.Layout.RawPropertyLayout" />
</parameter>
<parameter>
<parameterName value="@log_computerName" />
<dbType value="String" />
<size value="128" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%X{machine}" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_processTimeStamp" />
<dbType value="DateTime" />
<layout type="log4net.Layout.RawTimeStampLayout" />
</parameter>
<parameter>
<parameterName value="@log_group" />
<dbType value="StringFixedLength" />
<size value="1" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%message" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_type" />
<dbType value="StringFixedLength" />
<size value="1" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%message" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_eventId" />
<dbType value="Int32" />
<size value="32" />
<layout type="log4net.Layout.RawPropertyLayout" />
</parameter>
<parameter>
<parameterName value="@log_userId" />
<dbType value="Int32" />
<size value="32" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%identity" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_line" />
<dbType value="Int32" />
<size value="32" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%line" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_description" />
<dbType value="AnsiString" />
<size value="4000" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%message%newline %exception" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_source" />
<dbType value="AnsiString" />
<size value="4000" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%file" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_data" />
<dbType value="AnsiString" />
<size value="4000" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%logger" />
</layout>
</parameter>
<parameter>
<parameterName value="@log_addTimeStamp" />
<dbType value="DateTime" />
<layout type="log4net.Layout.RawTimeStampLayout" />
</parameter>
<parameter>
<parameterName value="@log_deviceId" />
<dbType value="StringFixedLength" />
<size value="10" />
<layout type="log4net.Layout.PatternLayout" />
</parameter>
</appender>
<appender name="asyncForwarder" type="Log4Net.Async.AsyncForwardingAppender,Log4Net.Async">
<appender-ref ref="AdoNetAppender" />
</appender>
<root>
<level value="ALL" />
<appender-ref ref="asyncForwarder" />
</root>
</log4net>
2)这是我的Global.asax.cs中的代码:
public class WebApiApplication : System.Web.HttpApplication
{
private static readonly ILog _log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
protected void Application_Start()
{
XmlConfigurator.Configure();
_log.Info("Service Started");
GlobalConfiguration.Configure(WebApiConfig.Register);
}
public static void Register(HttpConfiguration config)
{
// Web API routes
config.MapHttpAttributeRoutes();
}
}
3)将存储过程添加到db:
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE PROCEDURE dbo.procLogs_Insert
@log_timestamp datetime,
@log_recordNum int,
@log_computerName varchar(128),
@log_processTimeStamp datetime,
@log_group char(1),
@log_type char(1),
@log_eventId int,
@log_userId varchar(128),
@log_line int,
@log_description text,
@log_source text,
@log_data text,
@log_addTimeStamp datetime,
@log_deviceId char(10)
AS
BEGIN
SET NOCOUNT ON;
insert into dbo.BS_ApplicationLogs(LogTimestamp, RecordNum, ComputerName, ProcessTimestamp, LogGroup, [Type],EventId,UserId,Line,[Description],[Source],[Data],AddTimestamp,DeviceID)
values (@log_timestamp, @log_recordNum, @log_computerName, @log_processTimeStamp, @log_group, @log_type, @log_eventId, @log_userId, @log_line,@log_description,@log_source,@log_data,@log_addTimeStamp,@log_deviceId)
END
GO
问题:此存储过程应保存在SSMS中的哪个位置?当我保存存储过程时,它会自动将其默认为Documents \ SSMS,但我想将它保存在DB / Programmability / StoredProcedures文件夹下,但我没有看到它。但是,我确实成功执行了存储过程而没有任何错误。
4)将日志添加到global.asax.cs文件之外的app项目中的其他文件中。 Log4Net是否也知道记录这些内容?
所以,是的,我不确定我做错了什么,没有任何东西被记录到我的SQL Server表中。我是否错过了设置Log4Net的过程中的一步?
编辑:内部调试器说:
log4net: Created Appender [AdoNetAppender]
log4net: Created Appender [asyncForwarder]
log4net: Adding appender named [asyncForwarder] to logger [root].
log4net: Hierarchy Threshold []
log4net:ERROR [AdoNetAppender] ErrorCode: GenericFailure. Exception while writing to database
System.ArgumentNullException: Key cannot be null.
Parameter name: key
at System.Collections.Hashtable.get_Item(Object key)
at log4net.Util.PropertiesDictionary.get_Item(String key)
at log4net.Core.LoggingEvent.LookupProperty(String key)
at log4net.Layout.RawPropertyLayout.Format(LoggingEvent loggingEvent)
at log4net.Appender.AdoNetAppenderParameter.FormatValue(IDbCommand command, LoggingEvent loggingEvent)
at log4net.Appender.AdoNetAppender.SendBuffer(IDbTransaction dbTran, LoggingEvent[] events)
at log4net.Appender.AdoNetAppender.SendBuffer(LoggingEvent[] events)
什么钥匙?
答案 0 :(得分:4)
3)听起来你已经创建了存储过程,但它最终存在于Master数据库(Master / Programmability / StoredProcedures)中。
您应该选择DropDownList并从Master更改为您的数据库,或者您可以在存储过程之前使用语法USE YourDB
并单击Execute按钮:
USE YourDB
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE PROCEDURE dbo.procLogs_Insert
@log_timestamp datetime,
@log_recordNum int,
@log_computerName varchar(128),
@log_processTimeStamp datetime,
@log_group char(1),
@log_type char(1),
@log_eventId int,
@log_userId varchar(128),
@log_line int,
@log_description text,
@log_source text,
@log_data text,
@log_addTimeStamp datetime,
@log_deviceId char(10)
AS
BEGIN
SET NOCOUNT ON;
insert into dbo.BS_ApplicationLogs(LogTimestamp, RecordNum, ComputerName, ProcessTimestamp, LogGroup, [Type],EventId,UserId,Line,[Description],[Source],[Data],AddTimestamp,DeviceID)
values (@log_timestamp, @log_recordNum, @log_computerName, @log_processTimeStamp, @log_group, @log_type, @log_eventId, @log_userId, @log_line,@log_description,@log_source,@log_data,@log_addTimeStamp,@log_deviceId)
END
GO
答案 1 :(得分:1)
这是一个有效的文件,写入MS SQL服务器
它指的是用户定义的属性%property {xxx},它们填充在像
这样的代码中GlobalContext.Properties["user"] = Environment.UserName;
也许你可以用它替换你的一些属性来找出导致问题的那个
<appender name="AppenderDB" type="log4net.Appender.AdoNetAppender">
<bufferSize value="0" />
<reconnectOnError value="true" />
<connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=4.0.0.0, Culture=neutral" />
<connectionString value="Data Source=MYDB\DB;Initial Catalog=XXX;Integrated Security=True;" />
<commandText value="EXECUTE WriteLogEntry @time, @recipeName, @userId, @timeSeries, @loadTimeMs" />
<parameter>
<parameterName value="@time" />
<dbType value="DateTime" />
<layout type="log4net.Layout.RawUtcTimeStampLayout" />
</parameter>
<parameter>
<parameterName value="@recipeName" />
<dbType value="String" />
<size value="1024" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%property{recipeName}" />
</layout>
</parameter>
<parameter>
<parameterName value="@userId" />
<dbType value="String" />
<size value="20" />
<layout type="log4net.Layout.PatternLayout" value="%property{user}"/>
</parameter>
<parameter>
<parameterName value="@timeSeries" />
<dbType value="String" />
<size value="1024" />
<layout type="log4net.Layout.PatternLayout" value="%property{timeSeries}"/>
</parameter>
<parameter>
<parameterName value="@loadTimeMs" />
<dbType value="Int32" />
<size value="50" />
<layout type="log4net.Layout.PatternLayout" value="%property{loadTimeMs}"/>
</parameter>
`