Binsor : The Castle Windsor XML Configuration Killer
As you might have noticed from my previous post, I’m having a look at some of the stuff on my ever growing cool-tools-and-technologies-I-have-to-grock list. The next one that was high on my list is Binsor. It’s part of the Rhino Commons library and provides an internal DSL for configuring Castle Windsor, thus eliminating the need for XML configuration.
This DSL is written in Boo, a "wrist-friendly" statically typed programming language that targets the CLR. I’ve been playing around with this language for a couple of months now, and it’s gaining my respect ever since. Besides, Ayende is writing a book about Building Domain Specific Languages in Boo, so make sure to pick it up if you’re into DSL’s. Should be a fun read, no doubt.
Now, back to Binsor. Just because I have a huge aversion to XML, I’m always enthusiastic when I can eliminate some angled brackets. Let’s see some examples.
Suppose we have a class CustomerController that implements an interface called IController (couldn’t control my creativity there). I used to configure this class in XML like this:
<component id="CustomerController" service="MyWebApp.IController, MyWebApp" type="MyWebApp.CustomerController, MyWebApp"/>
Now, behold the simplicity of the Binsor DSL:
import MyWebApp Component("CustomerController", IController, CustomerController)
Nice, huh? They call it "wrist-friendly" for a reason. Let’s have another one. In my previous post, I needed to add some configuration to Castle Windsor in order to make use of the Rhino Commons repositories:
<!– Rhino commons –> <component id="nhibernate.repository" service ="Rhino.Commons.IRepository`1, Rhino.Commons.NHibernate" type="Rhino.Commons.NHRepository`1, Rhino.Commons.NHibernate"/> <component id="nhibernate.unit-of-work.factory" service ="Rhino.Commons.IUnitOfWorkFactory, Rhino.Commons.NHibernate" type="Rhino.Commons.NHibernateUnitOfWorkFactory, Rhino.Commons.NHibernate"> <parameters> <configurationFileName>web.config</configurationFileName> </parameters> </component>
Behold the Binsor equivalent:
# Rhino Commons Component("nhibernate.repository", IRepository, NHRepository) Component("nhibernate.unit-of-work.factory", IUnitOfWorkFactory, NHibernateUnitOfWorkFactory, configurationFileName: "web.config")
Binsor also supports facilities. Registering the WCF facility using XML configuration looks like this,
<facilities> <facility id="wcf" type="Castle.Facilities.WcfIntegration.WcfFacility, Castle.Facilities.WcfIntegration" /> </facilities>
while Binsor can do this in a single line of code:
Lets make it more interesting. Suppose you have lots and lots of controllers similar to the one in the first example. Every controller class implements the IController interface. Because Boo is a full-fledged programming language, you can make use of its entire syntax:
myWebAppAssembly = Assembly.Load("WindsorService") for type in myWebAppAssembly.GetTypes(): if typeof(IController) != type and typeof(IController).IsAssignableFrom(type): Component(type.Name, IController, type)
This small piece of code ensures that every controller that exists in my application is registered. From now on, every new controller class that I add to the application gets automatically configured. I don’t know about you, but I’m hooked.
From what I know so far, I noticed one small disadvantage: a lack of IntelliSense in Visual Studio. Whenever I’m messing around with Boo, I use SharpDevelop because it has extensive support for Boo. There is no support for Boo for Visual Studio (yet), but help is on the way. Maybe Charles Petzold is right? Maybe Visual Studio does rot the mind?
I’ll keep telling myself that I should not be so spoiled by IntelliSense, embrace the goodness of Boo and Binsor and stop acting like a cry-baby and take it like a man. Real programmers program in Notepad2 anyway :-).
Next item on the list …