Wednesday, November 24, 2010

Changing Default Logging Behaviour for different profiles with the Generic Host in NServiceBus

nservicebus logo I’ve been doing a lot of work with NServiceBus recently. I have to say it’s an amazing framework, saving my company hours and hours as we didn’t have to write out own Publish and Subscribe framework over the top of MSMQ. One of the tough parts about the framework is the learning curve to become familiar with all the setup and configuration options. Hence this post, I thought I’d share some of the things I’ve learnt over the last 2 weeks, lucky you eh?

Using the Generic Host


The NServiceBus documentation section explains why you’d want to use the generic host here. I decided to use the generic host so that I could easily debug my handlers and services, just like they were running as a windows service. However I ran into a few issues with regards to Logging and Dependency Injection when working with different profiles.
NServiceBus comes with 3 default profiles out of the box:

  • Lite  - This uses an in memory subscription model and by default logs debug level messages to the console. (Very Busy)
  • Integration - This uses MSMQ subscription model and by default logs info level messages to the console.
  • Production - This uses a database subscription model and by default logs errors to a rolling file.

I wanted to control the level of logging depending on the profile that was running. Also I wanted to Inject different behaviour depending on the profile that was running. Here’s what I found out thanks to the excellent NServiceBus community:

How to change Logging for different NServiceBus profiles

I found the default logging that comes out of the box for the Lite profile to be much too busy, I decided I didn’t need to see DEBUG level logging and also wanted the profile to log to a Coloured Console rather than boring old white. Here are the steps to achieve this:


  • Create a new class in your assembly somewhere, I called mine:

LoggingBehaviour.cs

  • You have to inherit from the IConfigureLoggingForProfile interface as follows:

using log4net.Appender;
using log4net.Appender;
using log4net.Appender;
using log4net.Core;
using NServiceBus;
 
namespace Company.Product
{
 public class LiteLoggingBehavior : IConfigureLoggingForProfile<Lite>
 {
  public void Configure(IConfigureThisEndpoint specifier)
  {
   SetLoggingLibrary.Log4Net<ColoredConsoleAppender>(null, a =>
    {
     a.AddMapping(
      new ColoredConsoleAppender.LevelColors
      {
       ForeColor = ColoredConsoleAppender.Colors.Green,
       Level = Level.Debug
      });
     a.AddMapping(
      new ColoredConsoleAppender.LevelColors
      {
       ForeColor = ColoredConsoleAppender.Colors.Red | ColoredConsoleAppender.Colors.HighIntensity,
       Level = Level.Error
      });
     a.AddMapping(
      new ColoredConsoleAppender.LevelColors
      {
       ForeColor = ColoredConsoleAppender.Colors.White,
       Level = Level.Info
      });
     a.Threshold = Level.Info;
    });
  }
 }
}
  • Lastly you have to update your app.config to include the section for NServiceBusLogging:

<section name="Logging" type="NServiceBus.Config.Logging, NServiceBus.Core" />
<Logging Threshold="INFO" />

  • That’s it.. now when you get an error you’re console will light up nice and RED.. so you know what’s going on:

Coloured_Console_Example

I think this makes it much clearer to detect issues when you’re coding.


How to change Behaviour using dependency injection for a profile

One of the services I was working on had an in memory repository for working locally and when live it used a SqlRepository. This again is very straightforward using the Generic host. Here are the steps to achieve this:


  • Create a new class in your assembly somewhere, I called mine:

DependencyInjectionBehaviour.cs

  • You have to inherit from the IHandleProfile interface as follows:

using NServiceBus;
using NServiceBus.ObjectBuilder; 
 
namespace Company.Product
{
 internal class LiteDependencyInjectionBehaviour: IHandleProfile<Lite>
 {
  public void ProfileActivated()
  {
   Configure.Instance.Configurer.ConfigureComponent<MemoryRepository>(ComponentCallModelEnum.Singleton); 
  } 
   
 }
   
 internal class ProductionDependencyInjectionBehaviour: IHandleProfile<Production>, IHandleProfile<Integration>
 {
  public void ProfileActivated()
  {
   Configure.Instance.Configurer.ConfigureComponent<SqlRepository>(ComponentCallModelEnum.Singleton); 
  
  } 
  
 }
}

  • That’s it.. now when running in Lite mode you won’t have to worry about configuring the connection to your database, etc.

Dependency Injection Example Code

As you can see from the above code, now when a reference IAmARepository as I’m running in Lite mode it’s using the MemoryRepository. To demo this I updated the default “FullDuplex” Example that comes with the NServiceBus download and I’ve saved it to my sky drive.


2 comments:

  1. Thanks, helped me setting up coloured console appender :)

    ReplyDelete
  2. No problem.. I think it now defaults to a coloured console. However it's useful to know how to inject different classes depending on the profile your're running the host as.

    ReplyDelete