kaba (2) [Avatar] Offline
#1
Just a hint for anyone trying to execute Listing 7.23 with Groovy 1.5.
This example will not work anymore because of a change in Groovy´s behaviour.

For example
assert [7495, 499, 1996] == invoices.items*.total()
throws
groovy.lang.MissingMethodException: No signature of method: java.util.ArrayList.total() is applicable for argument types: () values: {}
at Script2.run(Script2:41)

This error is not really surprising beause the members of "items" are Lists themself (and javas class ArrayList has no method named total()). It´s just a little less magic than before ...

For me as a newbee to groovy it took a while to find a solution. Now this line of code should look like this
assert [7495, 499, 1996] == invoices.items.flatten()*.total()

Finally I found a Jira (http://jira.codehaus.org/browse/GROOVY-2387) describing exactly this new behaviour. It seems to be a feature, not a bug smilie

So replace the last lines of example 7.23 with this ones to get a running example again (not pretty like the original code at some places, but it runs)

assert [5*1499, 499, 4*499] == invoices.items.flatten()*.total()

assert [["ULC"], [], []] ==
invoices.items.flatten()*.grep{it.total() > 7000}.product.name

def searchDates = invoices.flatten()*.grep{
it.items.any{it.product == ulc}
}.date*.toString()
searchDates.removeAll(["[]"])
assert [ "[" + ulcDate.toString() + "]"] == searchDates

regards,

Kai
Mittie (397) [Avatar] Offline
#2
Re: Listing 7.23 with groovy 1.5.0/1.51
Hi Kaba,

thanks a lot for posting. I consider this a bug in Groovy 1.5 and attached my comment to the JIRA issue.

Happy New Year
Dierk
kaba (2) [Avatar] Offline
#3
Re: Listing 7.23 with groovy 1.5.0/1.51
What about a new additional "powerful" operator which allows to work like spread-dot in groovy versions before 1.5? A "natural" string for a powerful operator could be "**.". This would allow to control the level of "magic" in a very compact (and therefore groovy) way.

It´s just an idea, but I think that this could be a quiet intuitive solution.

regards,
Kai
Mittie (397) [Avatar] Offline
#4
Re: Listing 7.23 with groovy 1.5.0/1.51
*hehe* nice idea.

I personally would prefer spread-dot simply working as in pre 1.5 but feel free to raise your proposal on the mailinglist.

cheers
Dierk
abickerton (2) [Avatar] Offline
#5
Re: Listing 7.23 with groovy 1.5.0/1.51
Right, Having been looking at this chapter for a while now. I'm confused. Why does the grep return a list of three items?

Surely this should only show the one item matching the condition in the closure. Can you make this a little clearer?
Mittie (397) [Avatar] Offline
#6
Re: Listing 7.23 with groovy 1.5.0/1.51
There are several greps involved. Which one are you referring to?

cheers
Dierk
abickerton (2) [Avatar] Offline
#7
Re: Listing 7.23 with groovy 1.5.0/1.51
This is this part of code in the previous 1.5 listing that's causing me some trouble[2].
assert [["ULC"], [], []] == invoices.items.flatten()*.grep{it.total() > 7000}.product.name

Surely the result of grep from the flattened list of item totals should only return those items that match a total > 7000 as the book goes on to describe.

Through some playing, I found that replacing the spead-dot with dot works, I'll go re-read the paragraph about the *. operator.

...
def products = invoices.items.flatten().grep{it.total() > 7000}.product.name
assert ["ULC"] == invoices.items.flatten().grep{it.total() > 7000}.product.name

def searchDates = invoices.flatten().grep{ it.items.any{ it.product == ulc } }.date.toString()
assert "["+ulcDate+"]" == searchDates

Thanks,
Alec
[1] Code sample submitted by kaba earlier in the thread.

[2] As I'm using Groovy 1.5 I have to say the loss of backward compatibility is somewhat worrying. Some might say a deal breaker when considering adoption of groovy in more production oriented applications.
I suspect a topic for the mailing list.