Beware the Elvis Operator in Groovy

While implementing a really simple caching mechanism in a Grails app, I came across what seemed like some odd behavior. I had an array of objects that would be built up within a function if not passed from the caller. To keep it as an optional argument, I had a default value of “null.”

def doStuff(arg1, arg2 = null) {
    arg2 ?: DomainClass.findAll(it.property == arg1)

    // Do stuff
}

This strategy was working most of the time, but there were still spurious database accesses whenever an empty array was being passed in. As it turns out, the spurious database accesses were occuring whenever the parent was passing an empty array for arg2. In Groovy, empty collections are falsy, as are empty strings and the number 0.

The fix was easy, just change the nice, simple, concise elvis operator with something far more java-esque, a null check.

def doStuff2(arg1, arg2 = null) {
    if (arg2 == null) {
        arg2 = DomainClass.findAll(it.property == arg1)
    }
    // Do stuff
}

With Groovy’s definition of truth, the elvis operator can sometimes lead to confusing results. Make sure that when you use it, it’s actually going to do what you want.