Wednesday, April 27, 2011

More Reasons Working with NServiceBus is Just Easier than WCF over MSMQ

We have some teams that went down the route of using WCF over MSMQ. Using a durable transport was the right thing to do for their process(accepting orders). We ran into a few issues along the way and had we used NSB to start with, we would have just avoided them.

IIS/WAS Hosting

We *thought* this would be a no brainer, but it really wasn't. Come to find out, if something goes wrong or your app pool recycles(every 24 hours or so guaranteed), you need to "warm-up" the service before it accepts messages. So Microsoft's answer to this is a warm-up extension to IIS or to host the service as a Windows Service. I think hosting in a Windows Service is a much better idea anyway as we weren't really using any of the IIS features anyway on the MSMQ transport. The thing is, had we used NSB out of the box we'd never have encountered such an issue.

Windows Service Hosting

Hosting this way gets you out of the warm-up jam. Unfortunately there is another problem if your shop uses SCOM like we do for monitoring. We haven't been able to get SCOM to monitor on the poison sub queues that WCF creates to put bad messages. We have some choices, which are call on MS to get this to work, build our own monitor, or just switch to NSB. I prefer the latter as we already have plenty of endpoints that we monitor just fine.

Summary

If you are thinking of using WCF over MSMQ make sure you host in a windows service and have a plan for when bad things happen. To us it makes sense to just retrofit those endpoints to NSB and avoid all the issues completely.

Wednesday, April 6, 2011

NServiceBus Customization Part 2: IWantToRunAtStartup

When NSB starts up it will look for all implementors of the interface IWantToRunAtStartup and call their Run() methods.  When NSB spins down it will also call the Stop() method of the same interface.  This gives us a good place to run expensive one time initialization code or to tweak out the bus prior to getting going.  A common usage of this interface is for the manual subscription to specific message types:
public IBus Bus { get; set; }

        #region IWantToRunAtStartup Members

        public void Run()
        {
            this.Bus.Subscribe<IProductUpdatedEvent>();
            this.Bus.Subscribe<IProductCreatedEvent>();
        }

        public void Stop()
        {
            this.Bus.Unsubscribe<IProductUpdatedEvent>();
            this.Bus.Unsubscribe<IProductCreatedEvent>();
        }

        #endregion
One thing that I would caution against doing in the Run() method is not exiting the method. I've seen cases where someone will go into an infinite loop and never exit Run(). Typically this is done to perform a task on a given interval. There are much better ways to do this, mostly commonly you can put a Timer into the container and wire into its events. If you never leave the Run() method, the Bus doesn't ever really startup and you will get some odd results.

Friday, April 1, 2011

NServiceBus 3.0 Details

The following content is paraphrased from the Yahoo Group:


First of all, I'd like to talk about the thing that will influence you the most. We're making every effort to make the use of NServiceBus (particularly it's auxiliary processes like the Timeout Manager, Distributor, and Gateway) much, much easier. What this means is removing much of complexity of using these capabilities by hosting them within the same host as your own process, but don't worry, we'll make it easy for you to turn them on and off using profiles. This will enable us to configure all the routing to these processes for you, but if you want, you can always go back to the manual approach in version 2.x. This is where I'll be investing most of my time.
 Second, there's the Data Bus feature that Andreas Öhlund (http://andreasohlund.net/) has been working on. As many of you know, most queuing transports have a limit on the size of message they can deliver - with MSMQ this is 4MB, with Azure it's 8KB. The Data Bus will allow you to transmit messages of an almost arbitrary size as it transmits the "data" portion on a separate infrastructure than the actual message. This is currently implemented using the file system but will be done using a database (RavenDB) as well - more on that in just a minute. The thing is that between remote sites, there often isn't the ability to have a shared file system or database, as the sites may not always be connected to each other. In order to resolve this issue, Andreas is also working on the Gateway to make it Data Bus aware - that and also able to support transports other than HTTP, like TCP and FTP.
 Third, there's the Azure integration that Yves Goeleven has been driving for some time now. For all those of you who've been looking for a simpler developer experience on Azure, Yves has really done it, abstracting away almost all of the underlying complexity behind your standard NServiceBus interfaces. You can find out more about this through his series of blog posts here:http://cloudshaper.wordpress.com/


Fourth is RavenDB integration. I'm happy to say that a licensing agreement has been reached that will allow users of NServiceBus Standard Edition to use RavenDB for things like Subscription Storage and Saga Persistence at no additional cost. This will save you from having to haggle with your DBAs anytime you want production-ready storage for NServiceBus - it'll give you a much more cohesive deployment without worrying about overloading your existing relational databases. I'm happy to welcome one of our newest committers, Jonathan Matheus (http://www.linkedin.com/in/jonathanmatheus), who is making this happen.
 The integration of RavenDB will enable us to stop merging NHibernate, but we'll still integrate with it out of the box. This will make it much easier for you to plug in your own version of NH instead of ours.
 Fifth is the Timeout Manager - one of the areas of NServiceBus that hasn't been as strong as the others. Jonathan Oliver (http://blog.jonathanoliver.com/ who has been ramping up his involvement over the past while) will be using our new RavenDB persistence to replace the use the input queue, which will dramatically increase the performance and robustness of the Timeout Manager.


We're also looking at stronger Visual Studio integration, possibly to the level of providing model-driven code/config generation. We'll see if it's feasible to get that done within the 3.0 timeframe, or whether that will be delivered as a separate download afterwards.
 Finally, the 3.0 release schedule looks something like this - Alpha by the end of April (primarily focusing on APIs), Beta in July, and a Release (or at least release candidate you can go live with) in September.