Tom Hollander's blog

patterns, practices and pontification

Instrumentation in Enterprise Library

Instrumentation in Enterprise Library

Rate This
  • Comments 58

Edit: This content applies only to the 1.x (January 2005 and June 2005) releases of Enterprise Library. Instrumentation behaves differently in the 2.x (January 2006) release.

Much of this has already been discussed in other forums, but there seems to be a fair bit of confusion about the instrumentation code in Enterprise Library, so I thought it would be worthwhile for me to touch on this too. I'll try to clear up how it currently works, why we chose to do it that way, and what we are thinking of doing to improve instrumentation in vNext.

One of the primary goals of Enterprise Library is to showcase best practices for enterprise .NET development. We try to do this in multiple domains, including architecture, code standards, unit testing and operations. This last one is especially important, as it's something that developers often ignore. As a developer it's very tempting to fall into the mindset that once it compiles and meets functional requirements, it's somebody else's problem. Then one day someone from your organization's operations team will call you at 11pm on a Friday night (probably when you're at the pub with your mates) and declare that your app is broken and your help is needed to fix it. And unless the application is properly instrumented (including logging errors, trace/diagnostic messages and health monitoring) it can be really, really hard to work out what's going on (and whose fault it is - because as soon as you can prove it's not to do with your app, you can go back to the pub!).

So instrumentation is very important, which is why we made sure we included it in the blocks - including event log messages, WMI events and performance counters. Of course you also need to instrument your applications as well, and we make a lot of this easier with the Logging & Instrumentation Application Block. However most kinds of instrumentation come at a cost - you generally need to run some kind of installation script and/or have administrator rights. In most cases this is something that can be dealt with, but we are aware that it is sometimes not an option - for example when deploying apps to hosted environments where you have limited rights and don't have the ability to run scripts.

So we tried to support both of these scenarios with Enterprise Library. Instrumentation is enabled by default, but to make sure everything is registered you'll need to run the Install Services script from the Start Menu, or run installutil over each assembly (possibly as a part of your own MSIs). When you install Enterprise Library with default settings, all of the code will be automatically compiled, but unfortunately we didn't run the Install Services script for you. This was an unfortunate outcome - but if you remember to run the script yourself then everything should work well.

If you are deploying to an environment where the instrumentation cannot be used, it's pretty easy to disable it, but you will need to recompile the code. Luckily all the instrumentation code is wrapped around conditional compilation directives, so you won't need to edit any source files directly. Just go into the Project Properties dialog for the Common project, and under Configuration Properties\Build, find the Conditional Compilation Properties property and remove ;USEWMI;USEEVENTLOG;USEPERFORMANCECOUNTER (or any combination of these that you don't want). Once you recompile, the relevant instrumentation code will be disabled. Of course, it is still possible to configure the Logging & Instrumentation Application Block to use WMI or Event Log, so make sure you also choose appropriate settings for your environment if you are using that block.

So, how are we thinking about improving the instrumentation? We're still in planning mode so we're open to suggestions, but at the top of the list are:

  • Make it possible to change the instrumentation behavior (turn it on and off) through configuration, rather than by recompiling the code
  • Run the Install Services script by default as a part of the installation process
  • Make the instrumentation more fine-grained, for example have separate performance counter instances for each Enterprise Library item such as a Database or Cache Manager

I hope this helps clarify things - please keep the suggestions coming!

This posting is provided "AS IS" with no warranties, and confers no rights.

  • I wonder why configuration through web.config wasn't introduced in the first place. When I read that you need to recompile the app, I immideately asked myself "what on earth for?".

    What is gained by having instruments conditioned with directives vs. web.config?

  • It was a scope/timing thing. However it's important to understand that the instrumentation we are talking about isn't the kind of thing that is designed to be turned off and on after deployment (unlike diagnostic logging, for example). The assumption is that this type of logging instrumentation should always be turned on, but we provide the conditional compile options to disable this if it's a deployment blocker.

    Tom
  • Probably some experienced programmers want to turn it off because it could increase performance. Because this could be possible, I think you should make it possible to turn off instrument through configuration. It's also a good idea to make the instrumenting more fine-grained. It could make it possible for us to watch the behavior on each block with the Performance monitor.
  • What's the proper way of using Tracing in an ASP.NET application?

    This doesn't work:

    using (new TraceContext(this.Context))
    {
    Logger.Write("Hello world");
    }

    I get a "Cannot implicitly convert type 'System.Web.TraceContext' to 'System.IDisposable'

    Thanks for any pointers.
  • Better deployment instructions. I was able to get asp.net logging via a flat file and event log working on my development machine, but getting it to work in a production environment is vague (actually I've been working on it a couple hours and still have no clue)
  • Adam -

    You should use
    using new(Tracer())
    {
    Logger.Write("Hello world");
    }
  • There is a problem when turning the USEPERFORMANCECOUNTER off (removing it from the project). When you try to CacheFactory.GetCacheManager(... , you get a runtime error in:
    Microsoft.Practices.EnterpriseLibrary.Caching.Instrumentation.CachingServiceItemTurnoverEvent.SetTotal(long totalItems)

    The CachingServiceItemTurnoverEvent.totalEntriesInstances is null. It's not hard to fix, but can you give a hint how much you tested without USEPERFORMANCECOUNTER, can I expect more runtime errors when removing theese properties?

    Erik
  • Hmmm...maybe people want to turn it off because the application you wrote on your development environment won't work in a production server? That's a pretty good reason.

    I can't believe that it wasn't made blatantly obvious. "Oh, btw, your stuff won't work anywhere other than your machine unless you recompile the Enterprise Library Common project with some objuscated settings removed. K? Thx."
  • The caching application block throws a runtime error on my deployment machines. The error message is not clear but I think the caching application block is trying to create an event log but the logged in user does not have admin permissions so this fails. I dont want the caching block to create event logs, is there a way to turn this off in the caching config file? documentation is a bit thin on the supported switches for caching ( btw I am not using the instrumentation block).
  • I took out those switches in the project properties as mentioned above, however, it then threw an error. I had no option but to modify the code and put a try with an empty catch block around it. The error is:
    An unhandled exception of type 'System.NullReferenceException' occurred in microsoft.practices.enterpriselibrary.caching.dll Object reference not set to an instance of an object.
    in class CachingServiceItemTurnoverEvent.cs in function SetItemsTotal at line cachingEvent.SetTotal(totalItems);
  • Mel: The code will work on a production machine if you have sufficient rights to run the installers. If you don't have these rights, you should know this well in advance of deployment.

    Tom
  • I get unhandled exceptions, I have yet to get this data access blocks to run. The sqlhelper code worked well in the past, now I have to redo all my code for the new blocks.

    I don't mind it writing to the event logs, I just wish you'd get an error message or some instructions on what to do beside 'recompile the code'.

    I'm not impressed by unhandled exception handling code by MS.

  • "sufficient rights" - how about some clarification?

    I'm an administrator of the box - wouldn't that be enough rights???

    Or do I have to give the rights to ASPNET and compromise my security?

    Confused with lack of documentation and vague responses online.
Page 1 of 4 (58 items) 1234