Boo

Book Review: DSLs in Boo

While I don’t spend a lot of time on the .NET platform anymore, I’m still a big fan of Boo. Having cut my teeth on Python many years ago, I’ve always enjoyed hip Pythonic languages and when Boo came out for the .NET platform way back when, I jumped on the opportunity to experiment with it and leverage it at client sites. What’s more, it’s no secret that I’m a fan of DSLs as I do find they can be quite powerful, for example, in leveraging natural language semantics that enhance the “user experience” such as with expressing intent.

Thus, when I had a chance to read Ayende Rahien‘s “DSLs in Boo“, I jumped at the opportunity, baby! Ayende does a great job of of introducing the notion of DSLs (interestingly, there isn’t a ton of literature here specifically about DSLs alone other than Martin Fowler‘s bliki and of course, Wikipedia) in the first chapter, specifically covering the various types of DSLs (i.e. internal, external, and he goes on to define graphical ones plus he reluctantly includes fluent interfaces). What’s more, he also explores why one would want to write an DSL. Here he covers a few reasons, but a quote stuck out regarding one particular reason, which is for expressing

rules and actions in a way that’s close to the domain and understandable to business people

This is, of course, the intent of easyb — that is, to express intentions in an easily understandable language that stakeholders can grasp.

After chapter 1, Ayende goes on to cover the basics of Boo, which, of course, would be needed should you want to actually create a DSL in Boo! It isn’t until chapter 4, however, that you start to get your hands dirty coding DSLs; nevertheless, I understand the need to introduce the various required concepts leading up to chapter 4. Thus, in chapter 4, a few high level examples are covered.

Later chapters go into some details about writing and maintaining DSL code; plus, in chapter 7, he unveils Rhino DSL, which is an open source project that facilitates authoring DSLs in Boo (Ayende, by the way, is a prolific coder — he’s all over the map in the .NET world). Chapter 8 finally covers testing a DSL, which I can attest as quite difficult but paramount to a DSL’s success and stability. He also goes on to cover versioning, which I found quite intriguing as backward compatibility is a double-edged sword.

What I find most interesting is the way in which a base language affects the resulting implementation of a DSL (i.e. the end result). That is, Pythonic DSLs still have the oft complained about “white-space issue.” For instance, here is a code snippet from the book for an order processing engine:

upon auth_denied:
  when preferred_customer:
       delay_order_until_payment_is_authorized "preferred customer benefit"
  when default_customer:
       cancel_order "no money, no order"

Note how the underlying language (Boo) forces the DSL to use spaces (rather than say brackets or def/do/end like calls), what’s more, underscores (i.e. _) are required so as to keep the compiler happy. It’s, in many ways, the same in something like easyb (which is, of course, backed by Groovy), which is essentially forced to use brackets and in one case, a comma like so:

given "a preferred customer", {
  //blah blah
}

Note how Groovy requires the DSL to include a comma between the description String and the Closure. Ruby, by the way, and in the case of something like RSpec, doesn’t have this requirement. For instance, in RSpec:

it "should return item enqueued" do
  @queue.enqueue("test")
  @queue.dequeue.should == "test"
end

Yet, notice the do and end! Needless to say, you can see similar influences in something like Scala too.

DSLs are interesting beasts and they’ve clearly affected productivity on various platforms (need I remind you that Rails is a DSL?). “DSLs in Boo” specifically explores DSLs on a specific platform, yet it’s still an interesting read. Because it’s my bag, I’m definitely looking forward to more books exploring DSLs as a main subject! All in all though, this is an interesting book regardless of your chosen platform. Can you dig it, man?

BDD in .NET

I ran across this hip .NET library for BDD some time ago: Specter. It’s built using Boo, which is a statically typed alternate language for the .NET CLI. Few people noticed (I think I might have been responsible for the sole page view measured), but I wrote an article about Boo for InfoQ.com in March of 2007 dubbed “Much ado about Boo“– Boo is definitely a hip language, which reminds me a lot of Python. If you’re coding on the .NET platform, give it a try and then give Specter a run!

boo! Java and .NET got scarier

This is totally mind-blowing, baby: via boojay (an extension to boo, which is a hip alternate language, based on Python, for the .NET platform) you can produce valid Java byte code. To my knowledge, this is a first– via an alternate language running on one platform, you can produce valid code for another target platform (i.e. .NET -> Java).

For instance, the author of boojay has already demonstrated how to create an Eclipse plug-in in boojay. Of course, there are plenty of copasetic languages for the JVM that produce Java byte code– Groovy, JRuby, Jython; however, these languages can’t (directly) produce valid byte code for the CLR. Is anyone up to this (oh so spooktacular, baby!!) challenge, man?

If it’s your bag and you want more information on Boo, check out:

.NET productivity just got scary

About a year ago, I started looking deeply into boo, which is a Python inspired language targeting the .NET CLI that enables rapid development of compliant Windows applications. With boo, you can quickly write developer tests, build GUIs, prototype applications– you name it– this language is frighteningly simple, man. Check out InfoQ’s “Much ado about Boo” and see for yourself how with its relaxed syntax, boo is a convenient platform for doing just about anything on the .NET platform quickly.

Boo is groovy two

As I’ve previously written about, developer testing with Boo can facilitate authoring tests quicker due to Boo’s relaxed hip Python-like syntax. Boo also integrates nicely with NAnt, meaning that tests written in Boo can easily be plugged into an automated build system that:

  1. compiles Boo code into a normal .NET assembly
  2. runs the corresponding NUnit tests
  3. reports the results

Compiling copasetic Boo code involves a bit a magic at this point as the current release doesn’t play well with the latest version of NAnt; therefore, in order to get things working properly, I had to use an older version of Boo (0.7.5) and NAnt 0.85-rc2. Once I had the correct versions, things moved quickly from there.

First, I had to load the Boo NAnt tasks with NAnt’s loadtasks task:

<target name="init">
  <loadtasks assembly="C:\\dev\\tools\\boo.0.7.5\\bin\\Boo.NAnt.Tasks.dll" />
</target>

Next, the booc task complies all Boo files into a .dll- in my case, I had to reference some additional love power libraries. For instance, I had to reference some .NET system libraries, which I would have figured the .NET runtime would have figured out (I’ve never had to reference a Java system library (rt.jar) when compiling Java or any of its manifold supported languages).

<target name="build" depends="init, setup">
  <booc target="library" output="${build.dir}/boo.words.dll">
    <sources basedir="src">
      <include name="**/*.boo" />
    </sources>
    <references basedir="./bin">
      <include name="nunit.framework.dll" />
      <include name="NDbUnit.Core.dll" />
      <include name="System.dll" />
      <include name="System.Data.dll" />
      <include name="System.Xml.dll" />
    </references>
  </booc>
</target>

Lastly, once things are compiled, the test target runs the compiled NUnit tests. Note, for some reason, the NDbUnit assembly must be in same directory where the compiled assembly resides in order to the tests to properly run.

<target name="test" depends="build">
 <copy todir="${build.dir}">
  <fileset basedir="./bin">
   <include name="NDbUnit.Core.dll" />
  </fileset>
 </copy>

 <nunit2 failonerror="false">
  <formatter type="Xml" usefile="true"
       extension=".xml"
	   outputdir="${build.dir}/results/" />
    <test assemblyname="${build.dir}/boo.words.dll"
          appconfig="mydefaulttest.config"/>
 </nunit2>
</target>

Boo’s smokin’ integration with .NET (and NAnt) makes this a compelling platform for building tests rapidly. Dig it?

Boo is groovy too

I remember when I first started investigating the .NET platform, I was fairly impressed with the CLI and the notion that code written in C# could be reused in VB.NET and vice versa. It’s been a number of years since the release of the .NET platform; however, it appears more and more superstars, besides the Mono team, are building upon the CLI and producing some copasetic stuff.

Take Boo, for instance, which is a dynamic language (that claims to barrow its syntax from Python but reminds me more of VB at this point) for the .NET platform. The neat-o thing about Boo is that any thing that runs on the CLI can be used within Boo and furthermore, that complied Boo code can be used within other languages, such as C#. This piqued my interest with regards to developer testing.

It seems to me that the #1 establishment excuse for not testing is ostensibly, the lack of time. If through tools and/or frameworks this perceived barrier can be removed or at least lowered then teams can be one step closer to building in quality as they code, rather than waiting for another entity, like QA or worse, a customer, to verify quality.

Because of Boo’s CLI-ness, Boo code can easily use NUnit- attributes and all. Understanding Boo’s syntax is quite easy, especially if you have familiarity with Python and as I mentioned previously, VB. Heck, a working knowledge of Groovy or for that matter, any dynamic language will help.

First of all, Boo follows the Pythonic indent scheme, whereby program structure is determined by one’s smokin’ indentations. Unlike Groovy’s brackets or Ruby’s end statements, Boo has no termination structures. Unlike C#’s using keyword or VB’s imports, Boo uses the Java-esque import statement and further spices it up with the ability to import from a particular assembly and even alias it with the as keyword.

Types are obviously optional and can be associated with a specific type with the as clause. For example, the hip variable fixture below is typed as OleDbUnitTest:

fixture as OleDbUnitTest

Other Boo syntax rules- instantiation doesn’t require new and constants are declared with the Java-esque final keyword. This is just a slice of the Boo syntax pie and surprisingly, the documentation is quite good.

Because it’s my bag, I thought I’d give Boo a spin by using Quality Lab’s NDbUnit along with NUnit to build a simple test case that inserts data via NDbUnit’s API and verifies the information was indeed committed to a database.

As you can see below, Boo is less verbose than normal C#– there are no semi-colons, brackets and fewer type declarations.

import NUnit.Framework
import NDbUnit.Core.OleDb
import NDbUnit.Core
import System.Data
import System
import System.Data.OleDb

[TestFixture]
class WordTest:

 final CONN = "Provider=SQLOLEDB...."
 final SCHEMA = "Dataset2.xsd"
 final XML = "XMLFile2.xml"
 fixture as OleDbUnitTest

 [SetUp]
 def configure():
  fixture = OleDbUnitTest(CONN)
  fixture.ReadXmlSchema(SCHEMA)
  fixture.ReadXml(XML)	

 [Test]
 def VerifyWordTableOle():

  fixture.PerformDbOperation(DbOperationFlag.CleanInsert)
  select = "select spelling from word where word.word_id = 2"

  adapter = OleDbDataAdapter(select , CONN)

  dta = DataSet()
  adapter.Fill(dta, "word")
  table = dta.Tables["word"]

  for row as DataRow in table.Rows:
    Assert.AreEqual("pugnacious", row[0],
	  "word spelling wasn't pugnacious")

Bottom line– this is a groovy language for the .NET platform that enables the quick construction of working code with minimal rules. Keep in mind too, this isn’t the only dynamic language available for those working with the CLI. There is the IronPython project, which is lead by Jython’s Jim Hugunin and even an IronRuby project. It seems to me; however, at this point, for those looking for the quickest mechanism to knock out tests, Boo is probably the front runner as it supports attributes (which it seems at this point, IronPython doesn’t) and therefore NUnit. Dig it?