A "domain specific language" is one in which a class of problems (or solutions to problems) can be expressed succinctly, usually because the vocabulary aligns with the that of the problem domain, and the notation is similar (where possible) to that used by experts that work in the domain.
What this really means is a grammar representing what you can say, and a set of semantics that defines what those said things mean. This makes DSLs just like other conventional programming langauges (e.g., Java) in terms of how they are implemented. And in fact, you can think of such conventional languages as being "DSL"s that are good at describing procedural solutions to problems (but not necessary good at describing them). The implications are that you need the same set of machinery to process DSLs as you do to process conventional languages, and that's essentially compiler machinery.
Groovy has some of this machinery (by design) which is why it can "support" DSLs.
See Domain Specific Languages for a discussion about DSLs in general, and a particular kind of metaprogramming machinery that is very helpful for implementing them.