log4net not working

2019-01-16 01:36发布

问题:

Hey I have this configuration in my web.config

<log4net>
    <appender name="LogFileAppender" type="log4net.Appender.FileAppender">
        <param name="File" value="mylog.log" />
        <param name="AppendToFile" value="true" />
        <layout type="log4net.Layout.PatternLayout">
            <param name="Header" value="" />
            <param name="Footer" value="" />
            <param name="ConversionPattern" value="%d [%t] %-5p %m%n" />
        </layout>
    </appender>
    <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender" >
        <layout type="log4net.Layout.PatternLayout">
            <param name="Header" value="[Header]\r\n" />
            <param name="Footer" value="[Footer]\r\n" />
            <param name="ConversionPattern" value="%d [%t] %-5p %m%n" />
        </layout>
    </appender>
    <root>
        <level value="DEBUG" />
        <appender-ref ref="LogFileAppender" />
        <appender-ref ref="ConsoleAppender" />
    </root>
</log4net>

but log4net is not working. My project compiles fine, and I get no errors debugging either. The lines where I tell to log.debug("somemessage") gets run fine, but I can't find the mylog.log file, so where is it?

回答1:

One gotcha for this type of thing is to make sure to add the XmlConfigurator attribute to the assembly by placing the following line in your AssemblyInfo.cs:

[assembly: log4net.Config.XmlConfigurator]

Otherwise log4net never activates.



回答2:

I guess that either log4net is not logging at all, or the file is not ending up where you expect it.

Firstly, have you actually called

XmlConfigurator.Configure()

anywhere in your code? If the xml snippet above is in the application configuration file, this call will do the trick. If the xml snippet is in it's own file, you'll need to use the .Configure(string) overload that takes the path to the file. Without this call (or apparently the assembly level attribute mentioned by Kirk Woll), then log4net won't be logging at all.

If you believe this is all done, and log4net should be logging, then maybe you should put a fully qualified path in for the log file while you debug further. That will let you be sure where the file should be.



回答3:

There is another small gotcha, see here: http://logging.apache.org/log4net/release/manual/configuration.html#dot-config

the [assembly: log4net.Config.XmlConfigurator] method doesn't work with app.config. If you configure log4net from app.config, you must use the log4net.Config.XmlConfigurator.Configure() method.



回答4:

Here is my checklist for when log4net is proving to be recalcitrant:

  • ensure that log4net.config file is copied to the bin\ folder when building (set to 'Copy if newer' in compiler)
    • when dealing with installed code, ensure that the log4net.config came along for the ride (set to 'Content' in compiler)
  • ensure that the user that the process runs as has write rights to the folder where the logs are to be written
  • if in doubt, give promiscuous permissions to c:\temp\ and get everything to log to there ()
  • fire up Sysinternal/Dbgview.exe to see if that tells you anything


回答5:

For an ASPNET MVC project adding

log4net.Config.XmlConfigurator.Configure();

to the Global.asax.cs also helps:

public class MvcApplication : System.Web.HttpApplication
{
    protected void Application_Start()
    {
        AreaRegistration.RegisterAllAreas();

        WebApiConfig.Register(GlobalConfiguration.Configuration);
        FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
        RouteConfig.RegisterRoutes(RouteTable.Routes);
        BundleConfig.RegisterBundles(BundleTable.Bundles);
        AuthConfig.RegisterAuth();

        **log4net.Config.XmlConfigurator.Configure();**
    }
}


回答6:

These are the steps which eventually got my file logging working:

  • -Check AssemblyInfo.cs contains the following attribute. [assembly: log4net.Config.XmlConfigurator]. This loads log4net.
  • Check the log directory has write permissions.
  • Check the logger has a format specified. This is done by checking each element in your configuration has a layout element specified. Eg:

<appender name="MainLogger"... <layout type="log4net.Layout.SimpleLayout"/>

  • Finally, try turning on log4net internal logging to enable console logging and checking the console. To do this, add <add key="log4net.Internal.Debug" value="true"/> to your appSettings.


回答7:

I've had experiences where logging systems fail silently without raising exceptions. I suppose this makes sense because if the logger is logging errors then how can it log an error that it's unable to perform logging?

So if the file isn't created on disk, start by looking into file system permissions to ensure the user your application is running under can write a new file to that disk location.

For testing purposes you might want to manually create the file on disk that should be written to and open up permissions for everybody to write to it. If the logger starts writing to it then you know it's permission based rather than configuration based.



回答8:

I tried all of the above but nothing worked. Adding this line in app.config's configSections section worked for me.

<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler,log4net, Version=1.2.15.0, Culture=neutral, PublicKeyToken=669e0ddf0bb1aa2a" />

Ensure that Version and PublicKeyToken is correct



回答9:

<param name="File" value="mylog.log" />

is saying "write mylog.log to actual folder". This means that if your webapp is under IIS, then log will be written to C:\inetpub\wwwroot\appname\mylog.log.

If log file is not there, then maybe account under which is app running doesn't have write permission on folder. You can run Process Monitor from SysInternals to see if and where a file is written.

Also run VS in debug mode, to see if any exceptions are thrown (Debug->Exceptions->CLR Exceptions, check Thrown).



回答10:

In my case I forget to set the log4Net.config file properties as "Content" so the file was not included in the deploy. So pay attention on it:

Compile action : Content


回答11:

Also after some hours, I figured out why it wasn't working for me...

i had:

public static class Program
{

    private static CommunicationManager _bcScanner = new CommunicationManager();
    private static ILog _log = LogManager.GetLogger(typeof(Program));
    private static SocketServer socketListener;

but it should be:

public static class Program
    {
        private static ILog _log = LogManager.GetLogger(typeof(Program));
        private static CommunicationManager _bcScanner = new CommunicationManager();
        private static SocketServer socketListener;

So make sure the ILog is on the first line....