I’m way late in linking to this, but it’s worth it.
Last October, a presentation by Martin Fowler from JAOO 2006 popped up on InfoQ (which does a great job of simulating the actual experience of being at the session with its video/slideshow integration) where he gave a very high-level overview of domain specific languages (DSLs). He really only scratched the surface, but it’s a great introduction for those that haven’t yet thought about DSLs much.
(Of course, that population is getting smaller by the minute thanks to Ruby (and Rails), since it builds in the metaprogramming facilities necessary to implement internal DSLs.)
I recently had occasion to re-watch the presentation. This time around, I took the time to scribble down some thoughts:
- I think he played up the potential role of DSLs as “configuration code” too much. Yes, you can tailor a DSL to provide primarily configuration data, and that’s very useful as far as it goes. However, internal DSLs (given an appropriately useful host environment) are able to provide levels of abstraction and composability that go way beyond configuration.
- I think that casting the Java example he showed as a DSL is really over the top, and is a result of overemphasizing the potential configuration role DSLs can play. As Mr. Fowler said, the line between an internal DSL and just a bunch of specific goal-driven coding in the host language is fuzzy. However, a big part of that line (and therefore whether an environment can reasonably host a DSL) is how well the host language’s existing constructs can be recast as sensible constructs in the DSL. The Ruby DSL example fits this criterion well, as its range (4..12, etc) and block constructs mapped well to the domain at hand. On the other hand, the Java example is Java, unapologetically so — the explicit object creation, the function calls, return statements, etc., simply do not map to the domain. The fact that the integers and strings being passed in those function calls can be recast as an actual configuration file should not lead us to think that Java configuration code is a functional DSL.
- At least in my experience, external DSLs are dead-ends. There’s just too much heavy lifting that needs to be done to consume external DSL “source files” and align their contents with the host language’s environment. True, internal DSLs need to conform to the syntax of their host environment, but the advantages of “symbolic integration” (as Mr. Fowler puts it) and the fact that you get your IDE’s functionality for free are just too compelling to outweigh any nitpicky syntax quibbles that one might have with any DSL-capable language. And, if those syntax quibbles are significant enough, and the problem the DSL is going to solve is significant enough to make you come close to considering building all of the cruft necessary to implement an external DSL, then go find yourself a secondary language/environment that provides a more palatable syntax, and hook everything up with IPC of some kind.