How to trace log level changes caused by .ConfigureAndWatch - log4net

Using .ConfigureAndWatch we have configured log4net to reconfigure its logging level without restarting application processes.
A process start we trace the currently configured log level to our trace file.
How can we detect and trace to our trace files the log level changes happening through .ConfigureAndWatch?

I just (re)discovered that ILoggerRepository has a ConfigurationChanged event.
Tracing log level changes from there works fine.
private static void repository_ConfigurationChanged(object sender, System.EventArgs e)
{
var currentTracelLevel = ((log4net.Repository.Hierarchy.Logger)_trace.Logger).EffectiveLevel;
_trace.InfoFormat("----------------------------- log4net level={0}", currentTracelLevel);
}

You can activate the log4net internal debugging, then you will receive messages from the ConfigureAndWatchHandler class when a change occurs, either on the console or in the trace output (see link for more information)
re your comment: In order to pull back the event into your own code and not rely on the console or trace output I'd recommend creating a custom trace appender that loops back into log4net. This way you can filter out messages you want to bring back into your own logs.

Related

Pre azure start up

We are sending all trace logs to our NLog logger. (with a trace listener)
Nlog is configured to work with DryIoC.
Locally this works perfect, however, in Azure (web app), the first trace message is logged, before we could create our DryIoc container. Even a PreAppStartMethodAttribute does not help, as the trace log has occurred even before the PreAppStartMethodAttribute.
Is there a way to do some initialization tasks before azure logs it's first trace message?
I found a work-around by using an async wrapper that prevents NLog from flushing the data until the container/configuration has been initiliazed.

Can built-in logging messages be turned off?

Once logging is configured with
LogManager.LogFactory = new Log4NetFactory(configureLog4Net: true);
it can be used anywhere with
ILog log = LogManager.GetLogger("foo);
log.Error("foo");
I get it. The problem is that Service Stack uses the same logger for various built-in internal messages. For example, if request is submitted for a non-existing route, Service Stack logs "ServiceStack.Host.Handlers.NotFoundHttpHandler - ::1 Request not found:".
Is there a way to disable or turn off those internal messages?
If you're using Log4Net you should be able to filter Log messages by type, otherwise some of ServiceStack's internal logging can be controlled in your AppHost by overriding:
public override void OnLogError(Type type, string message, Exception innerEx=null)
{
if (!SuppressLogs(type))
base.OnLogError(type, message, innerEx);
}
I've also just changed NotFoundHttpHandler to route messages to route error messages to OnLogError() from this commit so you'll be able to suppress messages by overriding the above method.
This change is available from v4.0.61 that's now available on MyGet.

logging/error handling inside a custom log4net appender

We have a internally-developed logging system, and we wanted to gain the benefits of log4net such as being able to use multiple appenders simultaneously. We decided to move the legacy logging system into a custom log4net appender. That worked great when the legacy system was configured correctly, but the legacy logger actually writes to a WCF client (making it slow for verbose logging, the reason we wanted to engage other log4net appenders), and recently the WCF configuration was not quite what it should have been. When this happened the application seemed to run ok, but obviously the custom appender for the legacy system was not working. The other appenders worked fine, but there was no output from the custom legacy appender and no error messages indicating that there was a problem.
What is the proper way to handle "recursive" logging, that is logging from inside a custom log4net appender? I tried a naive solution: grabbing log4net from its static object and logging inside the appender:
public class MyCustomAppender : AppenderSkeleton
{
protected override void Append(log4net.Core.LoggingEvent loggingEvent)
{
try
{
// something which throws here...
}
catch (Exception ex)
{
log4net.LogManager.GetLogger(this.GetType()).Error(this.GetType().ToString() + ": error during append", ex);
}
}
}
This was an abject failure, "System.Threading.LockRecursionException: Recursive read lock acquisitions not allowed in this mode." Fair enough; it was the naive solution.
I also tried:
this.ErrorHandler.Error(this.GetType().ToString() + ": error during append", ex);
in the exception handler, as it seemed possible it might be the right thing. Nothing obvious happened.
Is there a way to log errors through log4net inside an appender? Or do I have to do something like hard-code writing to the windows event log directly? Obviously there is great danger of infinite recursive descent, but I would think there would be some way of letting the operator know that one of the appenders failed to run.
JR
Of course as soon as I posted the question, I remembered something. log4net has a debugging switch inside the appSettings. I used this code:
this.ErrorHandler.Error(this.GetType().ToString() + ": error during append", ex);
inside the catch block, then set the magic setting on:
<appSettings>
<!--this is wonderful magic-->
<add key="log4net.Internal.Debug" value="true" />
</appSettings>
Now the ConsoleAppender (the other appender I was using) put out the custom appender exception message.
JR
Make sure you have this line at top:
using System.Threading;

Getting Azure Logs from role process

I've configured the Azure Diagnostics so that the logs get uploaded to a storage table. I'm using Trace.TraceXxx from my code and all works well.
Now I'm trying to add tracing from the Role OnStart() and OnStop() methods. I know that the tracing works as I see the lines in the Debug window when running in the emulator. But from the cloud deployment, it seems that these trace lines never get uploaded to the table. My guess is that it is somewhat related to TraceSources, as the only trace lines I've in the table come from the w3wp.exe source... Any hint ?
Thanks
Like you said you can add the trace listener using the WaIISHost.exe.config, but besides that you can also add the trace listener in code (you'll need a reference to Microsoft.WindowsAzure.Diagnostics.dll):
public class WebRole : RoleEntryPoint
{
public override void Run()
{
var listener = new Microsoft.WindowsAzure.Diagnostics.DiagnosticMonitorTraceListener();
Trace.Listeners.Add(listener);
...
}
}
Another way of setting up diagnostics is through the configuration file. If you created a VS solution recently, it will automatically create the diagnostics plug-in and configuration for the trace listener. With the config file (diagnostics.wadcfg) there is no code that needs to be written for the different data sources. Here is a link where you can get started and a sample file:
http://msdn.microsoft.com/en-us/library/gg604918.aspx
You cannot include custom performance counters right now and you need to make sure that you don’t try to allocate more than 4GB of buffer to anything (you can leave at 0), or it tends to fail.
Note, the time interval format (e.g PT1M). That is a serialization format, so PTXM is X minutes, while PTXS is X in seconds. You need to mark this as content and copy always in Visual Studio (place at root of project) so it gets packaged.
And here is a link to the three ways to setup diagnostics
http://msdn.microsoft.com/en-us/library/windowsazure/hh411541.aspx
Ranjith
http://www.opstera.com

How to exclude unwanted items from Azure Diagnostics Trace

I have setup Azure Diagnostics and using Trace to log any messages.
The problem is that when I go to the Azure WADLogsTable, I see that in addition to my messages there is a lot of crap that I want to eliminate.
How do I remove mesages like these?
IDependencyResolver.GetService<ASP._Page_Views_Account_Login_cshtml>() = ASP._Page_Views_Account_Login_cshtml
IDependencyResolver.GetService<System.Web.Mvc.ModelMetadataProvider>() = null
The only thing that I want to show are the things that I put there like this:
Trace.WriteLine("This is not good", "Information");
Make sure that your web.config does not contain any Trace config statements that send system messages to trace.

Resources