?
Solved

log4net help

Posted on 2014-03-25
9
Medium Priority
?
420 Views
Last Modified: 2014-03-25
Hi all,

I am trying to use the log4net to create logs for my application. I want to append debug messages and errors to both the console and a rolling log file.

Now I am having issues getting it set up. I am working from the tutorial here

http://www.codeproject.com/Articles/140911/log-net-Tutorial

I have copied the .dll to my bin directory of my web application.

I have the following code in my web.config;

  <configSections>
    <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net" />
  </configSections>

  <log4net>

    <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date{ABSOLUTE} [%thread] %level %logger - %message%newlineExtra" />
      </layout>
      <filter type="log4net.Filter.LevelRangeFilter">
        <levelMin value="INFO" />
        <levelMax value="FATAL" />
      </filter>
    </appender>

    <appender name="RollingFileAppender" type="log4net.Appender.RollingFileAppender">
      <file value="~/Logs/errorlogfile.txt" />
      <appendToFile value="true" />
      <rollingStyle value="Size" />
      <maxSizeRollBackups value="5" />
      <maximumFileSize value="10MB" />
      <staticLogFileName value="true" />
      <lockingModel type="log4net.Appender.FileAppender+MinimalLock" />
      <filter type="log4net.Filter.StringMatchFilter">
        <stringToMatch value="debug" />
      </filter>
      <filter type="log4net.Filter.StringMatchFilter">
        <stringToMatch value="error" />
      </filter>
      <filter type="log4net.Filter.DenyAllFilter" />
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date [%thread] %level %logger - %message%newline%exception" />
      </layout>
    </appender>

    <root>
      <level value="INFO" />
      <appender-ref ref="RollingFileAppender" />
      <appender-ref ref="ConsoleAppender" />
    </root>
  </log4net>

Open in new window


I then have an extended usercontrol class, which I add the following line (to save me adding to every ascx file).

public static readonly log4net.ILog log = log4net.LogManager.GetLogger

Open in new window


Now when I try to log a bit of info, i.e.;

log.Info("Info logging");

Open in new window


the file is not being created.

Could someone please advise me on what I am doing wrong here?
0
Comment
Question by:flynny
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 5
  • 4
9 Comments
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 39952912
Did you get completely through the tutorial? There is one additional line that needs to be included in your application:

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

Open in new window


This needs to be included outside of any namespace. The AssemblyInfo.cs file might be a good place to put it.

Also, I don't know if it was just a copy/paste error, but your variable declaration doesn't match what the tutorial says. You are missing a bit:

private static readonly log4net.ILog log = log4net.LogManager.GetLogger
    (System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

Open in new window

0
 

Author Comment

by:flynny
ID: 39952956
Sorry I forgot to put add this to my question. Yes I has added the following to my AssemblyInfo.cs file in the root of my project;

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

Open in new window


Also the reason I change from Private to public was because i have extended the usercontrol class to add the variable in and i got an error on accessing the log variable due to protection levels??
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 39952972
I'm sorry, I did not notice the change in access modifier, but that should be inconsequential. What I was referring to, however, was the bit inside of the parentheses.

When I put all of those elements together, the code worked for me:

Screenshot
0
Independent Software Vendors: We Want Your Opinion

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 

Author Comment

by:flynny
ID: 39952982
Hi,

Thanks for the reply.

Not that it should make a difference but I am working witha web application.

Just to put all the infor together currently;

I have the following in my web.config

<configSections>
    <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net" />
  </configSections>

  <log4net>

    <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date{ABSOLUTE} [%thread] %level %logger - %message%newlineExtra" />
      </layout>
      <filter type="log4net.Filter.LevelRangeFilter">
        <levelMin value="INFO" />
        <levelMax value="FATAL" />
      </filter>
    </appender>

    <appender name="RollingFileAppender" type="log4net.Appender.RollingFileAppender">
      <file value="~/Logs/errorlogfile.txt" />
      <appendToFile value="true" />
      <rollingStyle value="Size" />
      <maxSizeRollBackups value="5" />
      <maximumFileSize value="10MB" />
      <staticLogFileName value="true" />
      <lockingModel type="log4net.Appender.FileAppender+MinimalLock" />
      <filter type="log4net.Filter.StringMatchFilter">
        <stringToMatch value="debug" />
      </filter>
      <filter type="log4net.Filter.StringMatchFilter">
        <stringToMatch value="error" />
      </filter>
      <filter type="log4net.Filter.DenyAllFilter" />
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date [%thread] %level %logger - %message%newline%exception" />
      </layout>
    </appender>

    <root>
      <level value="INFO" />
      <appender-ref ref="RollingFileAppender" />
      <appender-ref ref="ConsoleAppender" />
    </root>
  </log4net>

Open in new window


then i have the following in my AssemblyInfo.cs

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

Open in new window


I also have now (fromgoogling) added the following to my global.asax file;

    void Application_Start(object sender, EventArgs e) 
    {
        log4net.Config.XmlConfigurator.Configure();
        
        // Code that runs on application startup
        log.Info("Debug: Starting Application");
        log.Debug("Debug: Starting Appplication");
    }

Open in new window


however the above messages are not being outputted to either output window or the text file??

Am I doing something wrong here? (there are no errors being thrown either).
0
 

Author Comment

by:flynny
ID: 39953047
ok I have managed to get a bit further now.

There seemed to be an issue with the file location (probably the ~)

<file value="~/Logs/errorlogfile.txt" />

Open in new window


changing this to

<file value="errorlogfile.txt" />

Open in new window


is now creating the log file in the root of the web application.

However, the initial .Info, .Debug and .Error calls are not adding to the file? BUT an error is being thrown in the application and the 'This is my error' log is being added to the file.

any ideas why this is happening? as I would like to add debug message through the application to track progress?

   private static readonly log4net.ILog log = log4net.LogManager.GetLogger
        (System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

    void Application_Start(object sender, EventArgs e) 
    {
        log4net.Config.XmlConfigurator.Configure();
        
        // Code that runs on application startup
        log.Info("Debug: Starting Application");
        log.Debug("Debug: Starting Application");
        log.Error("Debug: Starting Application");
    }
    
    void Application_End(object sender, EventArgs e) 
    {
        //  Code that runs on application shutdown

    }
        
    void Application_Error(object sender, EventArgs e) 
    { 
        // Code that runs when an unhandled error occurs
        log.Error("This is my error", Server.GetLastError());
    }

Open in new window

0
 
LVL 75

Accepted Solution

by:
käµfm³d   👽 earned 2000 total points
ID: 39953062
I am not an expert on log4net, but the way that I read the configuration file, you currently only have it set up to process INFO messages. This is due to the way you have <root> configured. The only "error" messages that will be output are those that are sent via the Info method, and only when the message contains the word "error". This is due to the <filter> nodes that are set up in the rolling file configuration.

I suspect that if you want to use the Error method, then you will need to include a <logger> node with a level set to Error.
0
 

Author Comment

by:flynny
ID: 39953115
Kaufmed,

first of all many thanks for your time on this. It was indeed the filters that were preventing the logging.

It appears the filters are case sensitive, so whilst I was ftrying to catch the filter 'debug' in the web.config I was sending 'Debug' in themessage and so it was ignoring it.

Many thanks for all your time and help.

One last question. Is it possible and where would I add a global

private static readonly log4net.ILog log = log4net.LogManager.GetLogger
        (System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

so that i could just call log.info, log.error from any .cs page?
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 39953124
Well, you made it static, so if you also make it public it will be accessible from any page. The only caveat is that you have to prefix the variable name with the containing class name. It probably would not make sense to leave it within any particular page, so I would suggest moving it to Global.asax. Then you simply would call it as:

Global.log.Error("some error");

Open in new window


...because Global is the class defined within Global.asax. If you don't have a Global.asax, simply add a new item to your project. It will be called "Global application class" in the list of items.
0
 

Author Closing Comment

by:flynny
ID: 39953182
thank you for your excellent support.
0

Featured Post

Command Line Tips and Tricks

The command line is a powerful tool at the disposal of every Linux user. Although Linux distros come with beautiful user interfaces, it's worthwhile to learn the command line because it allows you to do a number of things that you otherwise cannot do from the GUI.  

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction This article shows how to use the open source plupload control to upload multiple images. The images are resized on the client side before uploading and the upload is done in chunks. Background I had to provide a way for user…
Calculating holidays and working days is a function that is often needed yet it is not one found within the Framework. This article presents one approach to building a working-day calculator for use in .NET.
Sometimes it takes a new vantage point, apart from our everyday security practices, to truly see our Active Directory (AD) vulnerabilities. We get used to implementing the same techniques and checking the same areas for a breach. This pattern can re…
In this video, Percona Solution Engineer Rick Golba discuss how (and why) you implement high availability in a database environment. To discuss how Percona Consulting can help with your design and architecture needs for your database and infrastr…

719 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question