log4net problem under my solution - c#

Under my VS2010 solution I've this situation:
WEBSITE
Library1
Library2
On global.asax.cs I initialize the log4net configuration using:
private static log4net.ILog _logger = log4net.LogManager.GetLogger("globalASAX");
void Application_Start(object sender, EventArgs e)
{
// Code that runs on application startup
log4net.Config.XmlConfigurator.Configure();
_logger.Info("[APPLICATION START] " + DateTime.Now.ToString());
}
It works fine and Application start message is correclty available on log.txt file. The problem happens when I try to use log something on the classes available on DLL Library1 or Library2.
I added the row:
private static log4net.ILog _logger = log4net.LogManager.GetLogger(typeof(ImageRepository));
but when I try to all the _logger.error("blabla") nothing happens on log file; all properties of _logger are false (i.e. isdebugenable=false). How can I fix that? I followed the instruction available here:
http://logging.apache.org/log4net/release/manual/configuration.html
the configuration of log4net is under web.config file:
<log4net>
<appender name="RollingFile" type="log4net.Appender.RollingFileAppender">
<file type="log4net.Util.PatternString">
<conversionPattern value="log\explorer-log-%date{ yyyy.MM.dd.HH.mm.ss}-[%processid].log"/>
</file>
<appendToFile value="true"/>
<maximumFileSize value="1024KB"/>
<maxSizeRollBackups value="5"/>
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %level %logger - %message%newline"/>
</layout>
</appender>
<root>
<level value="DEBUG"/>
<appender-ref ref="RollingFile"/>
</root>
</log4net>
anyone can help me?
thanks,
Andrea

I suspect log4net cannot find the logger for your type ImageRepository. As a quick check create a named logger and try calling it.
private static log4net.ILog _logger = log4net.LogManager.GetLogger("FooLog");
And config
<root>
<level value="DEBUG"/>
<appender-ref ref="RollingFile"/>
</root>
<logger name="FooLog">
<level value="DEBUG"/>
<appender-ref ref="RollingFile"/>
</logger>

In theory this should work (as I'm sure you are aware). In general, however, there are two areas to check when you don't get anything logged to a file. The first area I would check would be the file appender itself. Text files can be locked, which can cause messages to be lost. The other thing I would check is to be sure that log4net is properly initialized in the library. It should be, but it doesn't hurt to check. If neither of these solutions help, try turning on the debugging of log4net itself to see what error messages are coming up. Here is a link that shows you how to turn on those messages:
http://haacked.com/archive/2006/09/27/Log4Net_Troubleshooting.aspx

Related

Log4net not working in multithreading in C#

hello friends i have added log4net package form nuget packages. for sync call log4net add logs in log file but when i am declaring a methods using Task its not working
<log4net>
<appender name="TestAppender" type="log4net.Appender.RollingFileAppender">
<file value="D:\log\logswebapi.log" />
<encoding value="utf-8" />
<appendToFile value="true" />
<rollingStyle value="Date" />
<layout type="log4net.Layout.PatternLayout">
<!--<conversionPattern value="%date %level [%thread] %type.%method - %message%n" />-->
</layout>
</appender>
<root>
<level value="All" />
<!-- If the following line is not included the log file
will not be created even if log4net is configured with this file. -->
<appender-ref ref="TestAppender" />
</root>
</log4net>
i have added this code in web.config file
private void AddLog(string str)
{
ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
Log.Info(DateTime.Now + " - " + str);
}
public string SendDocument(){
// send document logic
AddLog(send document done");
}
public string Response(){
Task.Run(() =>SendDocument()); // here i am calling this senddocument method in thread
}
in above code Response method i am calling send document methods in thread but logs are not added now how to resolve this issue ?
thanks in advance

Log4net not logging on Azure Webapp

For a web service, I have log4net configured and working fine locally but not when the webapp is deployed on Azure Webapp. The directory is created but there is nothing logged at the file..
Here is my config:
<log4net>
<appender name="RollingFile" type="log4net.Appender.RollingFileAppender">
<file value="log/sms.log" />
<appendToFile value="true" />
<maximumFileSize value="10MB" />
<maxSizeRollBackups value="10" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %level - %message%newline" />
</layout>
</appender>
<logger name="TheLogger">
<appender-ref ref="RollingFile" />
</logger>
Within my AssemblyInfo.cs I have:
[assembly: XmlConfigurator(Watch = true)]
At the Startup class i have :
public static ILog Logger { get; private set; }
public void Configuration(IAppBuilder appBuilder)
{
Logger = LogManager.GetLogger("TheLogger");
Logger.Info("Application start...");
}
Clearly my configuration is being picked up because in my log file is written the hour/date format and also Application start... but not the logging information.
What am i missing?
Make sure you don't forget to add the root configuration.
Are compiling for Debug and deploying in Azure in Release mode?
<log4net>
<root>
<level value="INFO" />
<appender-ref ref="RollingFile" />
</root>
<appender name="RollingFile" type="log4net.Appender.RollingFileAppender">
<!-- ... -->
</appender>
</log4net>
I had the same problem and found a solution. I had to replace these 2 lines of code in the Program class of the .Net Core API:
XmlDocument log4netConfig = new XmlDocument();
log4netConfig.Load(File.OpenRead("log4net.config"));
With this:
var logRepository = LogManager.GetRepository(Assembly.GetEntryAssembly());
XmlConfigurator.Configure(logRepository, new FileInfo("log4net.config"));
The reason is because in .Net Framework API's I used the assembly attribute to set this, now I need to do it like this.

Log4net sometimes creating two logs, one empty

Using the below configuration, about half of the time, I'm getting two logs per one, one empty. They differ in filename by one second (log.2015-03-09_11-50-25 vs log.2015-03-09_11-50-26)
I'm trying to have one log per run of the console application.
<log4net>
<appender name="Log" type="log4net.Appender.FileAppender">
<file type="log4net.Util.PatternString" value="C:\env\QA\Logs\consoleapp\log.%date{yyyy-MM-dd_HH-mm-ss}.txt"/>
<appendToFile value="true"/>
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %message%newline"/>
</layout>
</appender>
<root>
<level value="INFO"/>
<appender-ref ref="Log"/>
</root>
</log4net>
The latter log is the only one that's populated/written to.
Why is this happening? How do I fix it?
EDIT: Turns out i was instantiating a second logger in my code. When the instantiation occurred during a different second, a second log was created. The appender was working correctly.
I've seen something similar before - it's due to the second being specified in the filename, and the writes are occuring during the end of one second and the start of another.
<file type="log4net.Util.PatternString" value="C:\env\QA\Logs\consoleapp\log.%date{yyyy-MM-dd_HH-mm-ss}.txt"/>
should be
<file type="log4net.Util.PatternString" value="C:\env\QA\Logs\consoleapp\log.%date{yyyy-MM-dd}.txt"/>
In my last job, somebody set the second specifier in the log file name, and the production server came close to crashing trying the render the 150,000 files contained in the log folder.
Edit:
If you want to write once per run, you can add the following to your log4net configuration:
<rollingStyle value="Once" />
and you might need to set the appendToFile attribute to be false.
log4net one file per run
so your config would look like this:
<appender name="Log" type="log4net.Appender.FileAppender">
<file type="log4net.Util.PatternString" value="C:\env\QA\Logs\consoleapp\log.%date{yyyy-MM-dd_HH-mm-ss}.txt"/>
<appendToFile value="false" />
<maxSizeRollBackups value="-1" /> <!--infinite-->
<rollingStyle value="Once" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %message%newline"/>
</layout>
</appender>
I used user1666620's solution, but still got a .log.1 file.
Turns out I had the following line in my AssemblyInfo.cs file:
[assembly: log4net.Config.XmlConfigurator(Watch = true)]
Removing the above line fixed my issue. By the way, my program.cs looks like:
public static class Program
{
static Program()
{
// Initialize logging
log4net.Config.XmlConfigurator.Configure();
}
private static readonly ILog log =
LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
...
}

Setting up Log4Net to log output from a Class Library

I'm trying to setup Log4Net (this is my first time using Log4Net) to log to a text file in an assembly. I'm not getting any errors, but it's also not working. I can breakpoint the lines where I am logging my output and see that they are reached, but like I say nothing happens.
Where am I going wrong?
I have added the following to my packages.config file, inside the <packages> attribute:
<log4net>
<appender name="FileAppender" type="log4net.Appender.FileAppender,log4net">
<file value="c:\CTI\log.txt" />
<appendToFile value="true" />
<lockingModel type="log4net.Appender.FileAppender+MinimalLock" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date [%thread] %level %logger - %message%newline" />
</layout>
<filter type="log4net.Filter.LevelRangeFilter">
<levelMin value="INFO" />
<levelMax value="FATAL" />
</filter>
</appender>
<root>
<level value="DEBUG"/>
<appender-ref ref="FileAppender"/>
</root>
</log4net>
</configuration>
I have added the following line to AssemblyInfo.cs:
[assembly: log4net.Config.XmlConfigurator(Watch=true)]
I added the Log4Net assembly using NuGet and I am logging like this:
private log4net.ILog _Log;
_Log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
_Log.Debug("FooBar");
Like I say, no errors but nothing happens either.
What am I missing?
One thing that is wrong is that you are adding the log4net configuration section to the nuget config file (packages.config).
You can have the configuration in the app/web config or in a separate file to which you point from the appSettings, e.g.
configuration is in a file called config.log4net (the copy to output directory attribute of the file is set to copy always) and you add the following entry in app/web.config:
<add key="log4net.config" value="config.log4net"/>
If you don't want to depend on a web/app configuration, you can set the ConfigFileExtension property of the XmlConfiguratorAttribute attribute in AssemblyInfo.cs:
[assembly: log4net.Config.XmlConfigurator(ConfigFileExtension = "log4net", Watch = true)]
Then name the log4net configuration file the same as your exe/assembly plus the configured extension, e.g. MyApplication.exe.log4net or MyLibrary.dll.log4net
Another thing that is wrong is your appender filter. The range that you have set excludes DEBUG level, which you expect to log. Here are all logging levels:
ALL
DEBUG
INFO
WARN
ERROR
FATAL
OFF
As you can see, DEBUG is not between INFO and FATAL.

Log4Net - How to add a 2nd logger used only for specific sections of code

I'm using Log4Net 2.0, I have it working as required but which to add another logger for specific log statements. All logging is done to a single file appender. The change I want to make is that a 3rd party application fires events containing debug/error information, I can catch this information and whilst useful I feel it pollutes the normal application log file, and would instead prefer this to be stored in its own log file.
The end result I would like is a file called log-file.txt with all the logging from the application except the 3rd party logging. And a 2nd file called log-file-3rdparty.txt with logging only from the 3rd party application. The problem I have is setting up Log4Net to have 2 seperate loggers. I have already tried creating a 2nd LogFileAppender and adding it to the root however all this does in puts the same logging statements into both loggers.
Across the application we currently have the GetLogger statement as follows. This ideally needs to stay the same, so existing logging is unchanged. I need a new logger that is not affected by this statement, but is instead instantiated purely for 3rd party logging.
private readonly ILog _log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
And the App.Config as follows.
< log4net>
<logger name="MyApp.Logging">
<level value="DEBUG"/>
</logger>
<root>
<level value="ALL" />
<appender-ref ref="LogFileAppender" />
</root>
<appender name="LogFileAppender" type="log4net.Appender.FileAppender" >
<param name="File" value="log-file.txt" />
<param name="AppendToFile" value="true" />
<layout type="log4net.Layout.PatternLayout">
<param name="Header" value="
[Application started]
" />
<param name="Footer" value="[Application Finished]
"/>
<conversionPattern value="%date [%thread] %-5level %logger - %message%newline" />
</layout>
</appender>
</ log4net>
Can you help?
EDIT
If it makes any difference. The 3rd party log events are captured in the same class that some of my application log events are also fired from, this is because the class is responsible for controlling the 3rd part software. Is this an issue? I do have some inkling that log4net can differentiate which logger to create based on class names, and if that's the case do i need to refactor the 3rd party logging to its own class?
You can easily create a special logger like this:
ILog specialLogger = LogManager.GetLogger("SpecialLogger");
You can then configure the system to use a dedicated appender for this logger:
<logger name="SpecialLogger" additivity="false">
<level value="ALL" />
<appender-ref ref="SpecialLogFileAppender" />
</logger>
<root>
<level value="ALL" />
<appender-ref ref="LogFileAppender" />
</root>

Categories