Why are all my log4net levels false?

2019-02-07 17:38发布

问题:

I'm using log4net in my ASP.NET MVC3 project, but all logging properties such as IsDebugEnabled == false

In my AssemblyInfo I have:

[assembly: XmlConfigurator(Watch = true)]

In my log class I have

public Log4NetLogger()
{
    log4net.Config.XmlConfigurator.Configure();
    Logger = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
}

My related config stuff in Web.Config is:

<?xml version="1.0" encoding="utf-8"?>
<!--
  For more information on how to configure your ASP.NET application, please visit
  http://go.microsoft.com/fwlink/?LinkId=152368
  -->
<configuration>
  <configSections>
    <sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net" requirePermission="false"/>
       </sectionGroup>
  </configSections>

    <log4net debug="false">
      <appender name="AdoNetAppender" type="log4net.Appender.AdoNetAppender">
        <bufferSize value="100" />
        <connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
        <connectionString value="{removed}" />
        <commandText value="INSERT INTO Logging ([Date],[Thread],[Level],[Logger],[Message],[Exception]) VALUES (@log_date, @thread, @log_level, @logger, @message, @exception)" />
        <parameter>
          <parameterName value="@log_date" />
          <dbType value="DateTime" />
          <layout type="log4net.Layout.RawTimeStampLayout" />
        </parameter>
        <parameter>
          <parameterName value="@thread" />
          <dbType value="String" />
          <size value="255" />
          <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%thread" />
          </layout>
        </parameter>
        <parameter>
          <parameterName value="@log_level" />
          <dbType value="String" />
          <size value="50" />
          <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%level" />
          </layout>
        </parameter>
        <parameter>
          <parameterName value="@logger" />
          <dbType value="String" />
          <size value="255" />
          <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%logger" />
          </layout>
        </parameter>
        <parameter>
          <parameterName value="@message" />
          <dbType value="String" />
          <size value="4000" />
          <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%message" />
          </layout>
        </parameter>
        <parameter>
          <parameterName value="@exception" />
          <dbType value="String" />
          <size value="2000" />
          <layout type="log4net.Layout.ExceptionLayout" />
        </parameter>
      </appender>
      <!--Possible levels:-->
      <!--DEBUG-->
      <!--INFO-->
      <!--WARN-->
      <!--ERROR-->
      <!--FATAL-->
      <root>
        <level value="All" />
        <appender-ref ref="AdoNetAppender" />
      </root>
    </log4net>

  </applicationSettings>

</configuration>

I already got frustrated to a point of just wanting to do

public Log4NetLogger()
{
    Logger = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);


    Logger.IsDebugEnabled = true;
}

However of course Logger.IsDebugEnabled does not have any setters :/

What do I have to do to get this damn thing to work?

回答1:

I have had this same problem. I get around it by using the below line of code in the Application_Start method in the Global.asax.cs (assuming its a .Net web application)

log4net.Config.XmlConfigurator.Configure();


回答2:

Change your line to following in AssemblyInfo.cs:

[assembly: log4net.Config.XmlConfigurator(ConfigFile = "log4net.config", Watch = true)]

and put log4net's configuration in that file.



回答3:

Log4net expects its config section not to be grouped. Because in your config you have put your log4net section inside an ApplicationSettingsGroup (applicationSettings) log4net won't find its configuration. You can move the log4net section outside of the group or you can specify the group when calling XmlConfigurator.Configure:

XmlConfigurator.Configure(
    ConfigurationManager.GetSection(
        "applicationSettings/log4net") as XmlElement);


回答4:

It seems that you missed config file property setting changes Copy to Output Directory = "Copy always" Please check this setting image for more details. Config file setting Properties



回答5:

Log levels are case-sensitive, so instead of:

<level value="All" />

should be

<level value="ALL" />

I also find it much easier to create a separate log4net configuration file. Create a file called log4net.config and set the property of Copy to Output Directory to Copy always -- (copying your configuration from App.config into this file)

Then, when setting the configuration use:

XmlConfigurator.Configure(new System.IO.FileInfo("log4net.config"));



回答6:

I've never seen <level value="All" /> before, usually I just set value to one of the levels (since they're inclusive of the levels above them, or below them as you have them listed in your config, in the level stack). Something like this:

<level value="DEBUG" />

You might also try testing it with an explicit logger, just to see if the problem might be something else. Something simple adjacent to the appender node(s) like this:

<logger name="Log4NetTEST" >
  <level value="DEBUG" />
  <appender-ref ref="AdoNetAppender" />
</logger>

Then when testing it in your code you'd create the logger like this:

LogManager.GetLogger("Log4NetTEST");


回答7:

Change your line to following in AssemblyInfo.cs:

[assembly: log4net.Config.XmlConfigurator(Watch = true)]

Ensure log4net dll is added and Also put log4net's configuration in web.config file as

<configuration>
  <configSections>
    <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler" />
  </configSections>
  <log4net>
    <root>
      <level value="DEBUG" />
      <appender-ref ref="RollingFileAppender" />
    </root>
    <appender name="RollingFileAppender" type="log4net.Appender.RollingFileAppender">
      <file value="C:\LOGS\IDMUserRoleManagement\IDMUserRoleManagement.txt" />
      <appendToFile value="true" />
      <rollingStyle value="Size" />
      <maxSizeRollBackups value="5" />
      <maximumFileSize value="1000KB" />
      <staticLogFileName value="true" />
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%d{yyyy-MM-ddTHH:mm:ss} %-5p [%t] - %m%n" />
      </layout>
    </appender>
  </log4net>
</configuration>


回答8:

There is not setter for IsDebugEnabled as it is read only..

Use log4net.Config.XmlConfigurator.Configure(); in any method before you use log

and in app.Config the setting should be :

    <root>
      <level value="ALL" />
      <appender-ref ref="AppenderName" />
    </root>


回答9:

You're missing the opening tag for applicationSettings. That could be the cause



回答10:

In my case this was due to the fact that the <configSections> was not the first tag of the <configuration> section. This prevents the section name log4net being recognized. So the log instance shows the IsDebugEnabled and all the others as default boolean false.

This should be like this.

<configuration>
  <configSections>
    <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler,Log4net" />    
    <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
  </configSections>
<configuration>


回答11:

if class log file (Log4NetLogger) is in a alone class library, then the code: [assembly: log4net.Config.XmlConfigurator(C.... should be in the same class library.

for example: lib 1: my.web (a mvc project) lib 2: my.common (a class library project)

if you wrap logmanager code in my.common, then "[assembly: log4net.Config.XmlConfigurator(C..." SHOULD BE IN my.common, if you put it in my.web, it will not work!

Edit:

The usage of all config files (app.config, web.config, log4net.config, etc) is context based. So if you have a app calling a class library the config file that will be used is the .Config in the App project not the class library.

Another example, if you're Unit Testing an app the context is the Unit Test project and that's which config file will be used, not the app's config.



回答12:

You should have failed to initialize log4net in your application. This can be initialized explicitly by placing below at 'Application_Start',

log4net.Config.XmlConfigurator.Configure();



回答13:

I had the same problem. I was using a separate file and named it log.config. All I needed to do was mark the file property "Copy to Output Directory" to "Copy Always" in solution explorer in Visual Studio. That did the trick for me.