SpringOne Americas

Private Events

Blogs

View all Blogs >>
  • Andrew Glover

    Co-author of "Continuous Integration"

    Every once in a while the topic of code coverage surfaces, which more»

  • Stuart Halloway

    CEO of Relevance

    Programmers coming to functional languages for the first time cannot imagine life without variables. I address this head-on in the more»

  • Richard Monson-Haefel

    VP of Developer Relations, Curl Inc.

    more»

  • Neal Ford

    Application Architect at ThoughtWorks, Inc.

    The lowly whiteboard is one of my favorite tools for design work on projects: you can stand in front of it as a group, you can easily play... more»

  • Michael Nygard

    Agile technology leader and dynamicist

    Sizing, Danish Style Folks in telecommunications and operations research have used Erl more»

  • Matt Raible

    Creator of AppFuse and author of Spring Live

    It's been three weeks since I joined the realm of the unemployed. Fortunately, I more»

  • Alex Miller

    Sr. Engineer with Terracotta Inc.

    Or maybe that should be “a bit of final advice”. :) There was a more»

  • Vladimir Vivien

    Software Engineer / Consultant

    I finally downloaded the latest JDK 6 u 10 (download) recently. This is a significant re more»

  • Scott Leberknight

    Chief Architect at Near Infinity

    Re nae Bair's post on The Ranting Rubyis more»

  • Graeme Rocher

    Project Lead of the Grails Project & CTO of G2One

    Those crazy guys over at the Grails podcast interviewed me about various things ranging from being part of more»

  • Ted Neward

    Enterprise, Virtual Machine and Language Wonk

    Dustin Campbell, a self-professed "IDE guy", is speaking at the .NET Developer's Association of Redmond this evening, on the future of... more»

  • Pratik Patel

    Enterprise Architect

    There's been a 'backlash' of sorts brewing in the Java developer community over the past 2 years. From talking to my developer buddies around... more»

  • Howard Lewis Ship

    Creator of Tapestry and HiveMind

    Seems like the Mac has a huge number of RSS readers. For a while I was using Vienna, but it stopped working after a recent update (no blogs... more»

  • Mike Levin

    Software Developer specializing in Web2.0 websites

    (photo from more»

  • Brian Pontarelli

    Founder of Inversoft

    Just figured out how to get git tab completion working in zsh on a Mac. Turns out that the completion scripts use a bunch of extra git... more»

  • Erik Doernenburg

    Principal Consultant @ Thoughtworks

    If you are somebody who writes code you probably know that moment when you look at some code you didn’t write, or some code you wrote a... more»

  • Kirk Knoernschild

    Software Developer & Mentor

    more»

  • Brian Goetz

    Author of Java Concurrency in Practice

    I live in an AT&T-free state, so I have not had access to the cult that is iPhone. But recently, in preparation for AT&T moving... more»

  • Matthew Bass

    Software Developer & Entrepreneur

    Can Sphinx and foxy fixtures place nicely together? Due to the way Sphinx indexing works, foxy fixtures will often slow down the indexing... more»

  • Jason Rudolph

    Author of Getting Started with Grails

    I had the more»

  • Ryan Shriver

    Business and Technology Consulting

    more»

  • Nathaniel Schutta

    Author, speaker, software engineer focused on user interface design.

    Today we learned something important, the NTSB announced the more»

  • Jeff Brown

    SpringSource Engineering And Professional Services - Groovy and Grails Developer

    Strange enough title.Let's start with a hypothetical conversation between a geeky developer and his much less geeky wife: more»

  • Jared Richardson

    Agile coach and co-author of Ship It

    Jurgen Appelo has an ongoing interview series on his blog. He's published a lot of very smart people and I'm honored to squeak in too! ;) more»

  • David Bock

    Principal Consultant, CodeSherpas Inc.

    I have been setting up a rock-solid server cluster for a client and ran into an interesting issue trying to install Phusion Passenger onto... more»

  • Pramod Sadalage

    Co-author of "Refactoring Databases:Evolutionary Database Development"

    Consider this Hibernate mapping @Column(name = "qReferenceId") public Long getQReferenceId() { return qReferenceId; more»

  • Craig Walls

    Author of Spring in Action

    At one time not too long ago, I wasn't a big fan of annotations. But then I let my guard down and even started liking them. But now I'm... more»

  • Kenneth Kousen

    President of Kousen IT, Inc.

    In this entry in my “Making Swing Groovy” series, I want to talk about threading issues. Specifically, more»

  • Venkat Subramaniam

    Founder of Agile Developer, Inc.

    I wrote a four part article for Java World on creating DSLs in Java and Groovy. For your convenience, I decided to list the links to those... more»

  • Jason Harwig

    Senior Software Engineer at Near Infinity

    The most popular entry I've written at Near Infinity has been the more»

  • John Heintz

    Principal Consultant with New Aspects of Software

    In a recent discussion interview questions came up, here's my favorite one.To set some context this question is designed to gauge the abst more»

  • Mark Johnson

    Director of Consulting at CGI

    At the Columbus NFJS show held on July 25-27th during one of the BOF sessions Dave Bock, Scott Davis and I discussed unit tests vs functional... more»

  • Joseph Nusairat

    Author of Beginning JBoss Seam & Co-Author of Beginning Groovy & Grails

    Well i am assuming Apress has the most random site in the world at times.But today only they have our recent book, Beginning Groovy & Grai more»

  • Keith Donald

    Lead of Spring Web and Creator of Spring Web Flow

    I am pleased to announce that Developing Rich Web Applications with Spring, a three-day bootcamp lead by SpringSource engineers on web... more»

  • Pete Behrens

    Organizational Agility Coach

    Marti nig & Associates Methods & Tools group recentl more»

  • Brian Sam-Bodden

    Java author, Ruby geek and Open Source Advocate

    In this installment we are going to build the Dashboard page of the Tempo application. T more»

  • Mark Fisher

    Spring Integration Lead

    In my recent post, I had mentio more»

  • Ron Bodkin

    Chief Software Architect, Quantcast

    I'm looking forward to speaking at The Rich Web Experience conference in San Jose next month. The event runs from September 7th through 9th.... more»

  • Mark Goodwin

    Web Application Security Specialist

    We've already looked at one of the two big problems posed by anti DNS pinning on Java applets; because there's rebinding on the applet and... more»

  • Scott Davis

    Author of "Groovy Recipes" & TDD Expert

    Every time I see a live show at the Denver Botanic more»

  • Romain Guy

    Java User Interface expert.

    more»

  • Ramnivas Laddad

    Author of AspectJ in Action, Principal at SpringSource

    InfoQ.com has published my AOP myths and realities talk recorded at a No Fluff Just Stuff conference. InfoQ.com founded by Floyd Marine more»

  • David Geary

    Author of Graphic Java and co-author of Core JSF

    The 2006 NFJS tour kicked off t more»

  • Kito Mann

    Editor-in-chief of JSF Central and the author of JSF in Action

    I miss the latest.integration keyword from ivy.... more»

  • Jason Hunter

    Author of Java Servlet Programming

    I just posted the JDOM 1.1 release for download. This release includes about 20 improvements and bug fixes. more»

Using Groovy's FactoryBuilderSupport to Build Internal DSL

Posted by: Vladimir Vivien on 03/04/2008

Using Groovy's FactoryBuilderSupport to Build Internal DSL


Couple of weeks ago at the Groovy/Grails Experience conf, Groovy's meta programming was a big theme there. Since then, I blogged about using Groovy's built-in Meta Object Protocol (MOP) mechanism to create a simple XML builder. Then I got curious about other builders such as Swing and SwingX. Talking to James Williams (SwingXBuilder creator), I found out that Groovy's FactoryBuilderSupport interface is designed specifically to allow developers create builder-style DSL. While the FactoryBuilderSupport provides a rich interface to create your own DSL, examples are hard to come by. Thankfully, James had just created another builder called Java3DBuilder which uses the FactoryBuilder interface and a good starting point. This shows a small example on using the FactoryBuilderSupport.

The FactoryBuilderSupport along with Groovy's Factory interface offer a structured approach to constructing internal DSL's. Unlike tapping directly into MOP to manage your DSL nodes, the factory approach requires you to explicitly register by name each node with the FactoryBuilder. The Factory interface exposes event callbacks to intercept different phases of node traversal by the FactoryBuilder which lets manage state and behavior of your DSL. Here is how Groovy's website describes the Factory interface and its methods:


A quick note about newInstanceMethod() - when the factory builder creates a new instance of your node, it will pass in these params: an instance of the factory builder, the name of the node being processed, an argument value (if used as the form node(arg) ), and optionally a map if the node is used as node(key:value...).

Saying Hello, the DSL Way
So, using the information above (and some some sleuthing on my part), I was able to figure out how to use the FactoryBuilderSupport class to build a simple DSL to display a greeting message. So, the first thing is to specify how the language will look and feel. Since we are using the builder pattern, our DSL will have the familiar construct we have seen in other builders:

builder.using(a given language) {
greet(person1)
greet(person2)
greet(person4)
...
greet(personN)
}

A call to builder.build() will print out the greeting in the proper language.

The Code

First, let us look at the backing structure that will support our DSL. It consists of a Person object and GroupGreeter class. The latter actually stores the persons we want to greet and apply the logic to build the greeting string.

The greetings can be in several languages including English, French, German, Spanish, Italian, and Portuguese. The greetings map (line 9)stores the greeting text as well as the conjunction to use when we are greeting more than one person.

Disclaimer: I am not a language geek. This translation is straight from Google Language Tools . So, I am not responsible for greetings that are colloquially incorrect or used in the wrong context!

On to the Builder

The next code snippet shows the FactoryBuilderSupport and the factories that it manages. Each node in your DSL is implemented by a factory instance. In our example, the nodes are are using and greet. Node using is registered with GroupGreetingNode and greet is registered with class GreetingNode.



GroupGreetingNode represents the parent node. It sets up a GroupGreeter object (see previous section) with the language passed in as its argument and returns the newly created GroupGreeter object. The GreetingNode is a child node of the GroupGreetingNode. When the "greet" node is encountered, the builder calls newInstance() on GreetingNode and a new instance of the Person object with the name as an argument and returns the newly created person back to the builder. The builder will eventually call setParent() on the GreetingNode. At that point, the person object that was created in is added to the parentNode (which is an instance of GroupGreeter). That's it!

Running the Code
The following shows two usage of the Greeting DSL
The code above produces

Hallo, Jon, David und Ella
Salut Mireille

Observations

  • The semantic for your DSL requires an appropriately fitting backing API and data structure
  • Model your backing data structure close to your DSL. It makes implementation of the builder simpler.
  • If you can't change the backing API, try model your DSL syntax and semantic close to your API.
  • FactoryBuilderSupport and Factory simply facilitates the traversal of the DSL nodes. They should not be used to implement the backing data structure.
  • How you process the nodes is subjective and depends on how your backing data model is structured.
  • Process data at the intended node level. So, a child node should process all of its data not pass it to the parent.

Conclusion
There's no doubt that Groovy makes developing DSL easy. As we have seen the combination of the FactoryBuilderSupport class and the Factory interface provides a structured approach to creating DSL that conforms to the builder pattern. In this write up I demonstrated how to create a simple DSL to print out greeting on the screen. The same techniques used here are used to create more complex DSL such as Java3DBuilder.

References
0. Download Groovy source code - http://vladimirvivien.com.s3.amazonaws.com/GreetingBuilderDemo.groovy
1. Dynamic Groovy - http://groovy.codehaus.org/Dynamic+Groovy
2. Groovy FactoryBuilderSupport - http://groovy.codehaus.org/FactoryBuilderSupport
3. Jame William's Java3DBuilder - http://www.jameswilliams.be/blog/entry/60

Hope you enjoyed it!

be the first to rate this blog


About Vladimir Vivien

Vladimir Vivien is a software engineering living in Tampa, FL (US) currently working in the healthcare industry. Past and current experiences include development in Java and C#.Net for industries including publishing, finacial, and heathcare.

Vladimir's interests include JMX, OSGi, Rich-Client technologies such as XUL and OpenLaszlo, and dynamic languages including Groovy, Python, JavaScript. He thinks the future direction of the Java language is hidden in Groovy.

Contact: vmatters @ gmail dot com.