Sunday 28 April 2013

Semantic Logging Application Block in Enterprise Library 6.0

Enterprise Library 6.0 has been released. You can find most of the stuff you need to know about it here. One of the most exciting feature of pack is Semantic Logging Application Block. It was available in its CTP form till now but is now an official release as part of EntLib.
 
At its core, it presents pretty powerful set of classes which are nicely decoupled from each other and allow LOB applications to log information (semantically, no pun intended) in 2 ways - in-process and out-of-process. In-Process logging uses ObservableEventListener to efficiently log information while Out-Of-Process logging uses combination of ETW infrastructure and Semantic Logging Service (available as a separate download here).
 
So, I decided to create a simple sample to experience its capabilities. Below is the code I used -
 
A simple Business Class -
public class BusinessClass
    {
        public void DoBusinessEvent(int token)
        {   
            if (token % 2 == 0) { 
                BusinessClassEventSource.Instance.EvenTokenEventOccurred(token); 
            }
            else { 
                BusinessClassEventSource.Instance.OddTokenEventOccurred(token); 
            }
            // Do something interesting like counting to 10.
        }
    }
 
A Custom Event Source -
 
public class BusinessClassEventSource : EventSource
    {
        private const int Even_Token_EventId = 1;
        private const int Odd_Token_EventId = 2;
        private static BusinessClassEventSource businessClassEventSource = new BusinessClassEventSource();
 
        private BusinessClassEventSource()
        {
           //nothig
        }
 
        public static BusinessClassEventSource Instance
        {
            get
            {
                return businessClassEventSource;
            }
        }
 
        public void EvenTokenEventOccurred(int token)
        {
            this.WriteEvent(Even_Token_EventId, token.ToString());
        }
 
        public void OddTokenEventOccurred(int token)
        {
            this.WriteEvent(Odd_Token_EventId, token.ToString());
        }
    }
 
A custom EventListener -
 
public class BusinessClassEventListener : EventListenerIObservable<EventEntry>
    {
        public IDisposable Subscribe(IObserver<EventEntry> observer)
        {
            return null;
        }
 
        protected override void OnEventWritten(EventWrittenEventArgs eventData)
        {
            Console.WriteLine(eventData.ToString());
        }
    }
 
And the main program -
 
class Program
    {
        static void Main(string[] args)
        {
            var listener1 = Microsoft.Practices.EnterpriseLibrary.SemanticLogging.ConsoleLog.CreateListener();
            listener1.EnableEvents(BusinessClassEventSource.Instance, EventLevel.LogAlways);
 
            var listener2 = new BusinessClassEventListener();
            listener2.EnableEvents(BusinessClassEventSource.Instance, EventLevel.LogAlways);
 
            BusinessClass businessClass = new BusinessClass();
            businessClass.DoBusinessEvent(100);
            businessClass.DoBusinessEvent(101);
            
            listener1.DisableEvents(BusinessClassEventSource.Instance);
            listener2.DisableEvents(BusinessClassEventSource.Instance);
 
            Console.ReadLine();
        }
    }
 
The good thing about SLAB is that we can write custom Formatters, Event sinks etc if out of the box capability does not suffice. SLAB provides default wiring to leverage SQL Server, Flat File, Console, Rolling Flat File, Windows Azure Table and others as storage for logged information.

4 comments:

  1. Great,

    two questions:

    a.) Can I use it in Wcf Service ??

    Wcf Service hasn't Main method.

    b.) Can I use eventListener to log to a file (rolling)

    Any sample about it?

    ReplyDelete
  2. WCF Service does not have Main method. You can use ServiceBehavior or EndPointBehavior to enable create listeners and enable Events.

    Yes, you can use write to rolling log file as well. You will need to change the implementation of OnEventWritten method.

    ReplyDelete
  3. Any full sample using ServiceBehavior or EndPointBehavior to enable create listeners and enable Events.?

    Any sample using implementation OnEventWritten for creating rolling file without using Ent.Lib ?

    Thx

    ReplyDelete
    Replies
    1. I'm trying to do the same. How can I use a ServiceBehavior to enable create listener for SLAB?

      Delete