Whats new in Groovy 2.0?

119
Main sponsor What’s New in Groovy 2.0? Guillaume Laforge Groovy project Manager

description

Presentation on Groovy 2.0 given at the 33rd Degree conference in Krakow, Poland, in March 2012.

Transcript of Whats new in Groovy 2.0?

Page 1: Whats new in Groovy 2.0?

Main sponsor

What’s New in Groovy 2.0?Guillaume  LaforgeGroovy  project  Manager

Page 2: Whats new in Groovy 2.0?

@glaforge

Guillaume Laforge• Groovy Project Manager at VMware

• Initiator of the Grails framework• Creator of the Gaelyk

and Caelyf toolkits

• Co-author of Groovy in Action

• Follow me on...• My blog: http://glaforge.appspot.com• Twitter: @glaforge• Google+: http://gplus.to/glaforge

2

Page 3: Whats new in Groovy 2.0?

@glaforge

Agenda

• What’s new in Groovy 1.8?–Nicer DSLs with command chains–Runtime performance improvements–GPars bundled for taming your multicores–Closure enhancements–Builtin JSON support–New AST transformations

3

Page 4: Whats new in Groovy 2.0?

@glaforge

Agenda

• What’s cooking for Groovy 2.0?–Alignments with JDK 7

• Project Coin (small language changes)• Invoke Dynamic support

– Continued runtime performance improvements

–Static type checking–Static compilation–Modularity

4

Page 5: Whats new in Groovy 2.0?

@glaforge

Command chains• A grammar improvement allowing you

to drop dots & parens when chaining method calls–an extended version of top-level statements like println

• Less dots, less parens allow you to –write more readable business rules–in almost plain English sentences

• (or any language, of course)

5

Page 6: Whats new in Groovy 2.0?

@glaforge

Command chains

 turn  left    then  right  

6

Page 7: Whats new in Groovy 2.0?

@glaforge

Command chains

 turn  left    then  right  

Alternation of method names

6

Page 8: Whats new in Groovy 2.0?

@glaforge

Command chains

 turn  left    then  right  

Alternation of method names

and parameters(even named ones)

6

Page 9: Whats new in Groovy 2.0?

@glaforge

Command chains

 turn  left    then  right  

6

Page 10: Whats new in Groovy 2.0?

@glaforge

Command chains

 turn  left    then  right            (        ).        (          )

Equivalent to:

6

Page 11: Whats new in Groovy 2.0?

Look Ma!No parens, no dots!

Page 12: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2.pills,  of:  chloroquinine,  after:  6.hours

Before... we used to do...

8

Page 13: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2.pills,  of:  chloroquinine,  after:  6.hours

Before... we used to do...

Normal argument

8

Page 14: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2.pills,  of:  chloroquinine,  after:  6.hours

Before... we used to do...

Normal argument Named arguments

8

Page 15: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2.pills,  of:  chloroquinine,  after:  6.hours

Before... we used to do...

Normal argument Named arguments

Woud call:

def  take(Map  m,  Quantity  q)

8

Page 16: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2    pills  of    chloroquinine    after    6  hours

9

Now, even less punctuation!

Page 17: Whats new in Groovy 2.0?

@glaforge

Command chains

take  2    pills  of    chloroquinine    after    6  hours        (  ).          (    ).                            (          ).  (          )

9

Now, even less punctuation!

Page 18: Whats new in Groovy 2.0?

@glaforge

Command chains

//  Java  fluent  API  approachclass  RegimenBuilder  {        ...        def  take(int  n)  {                this.pills  =  n                return  this        }

       def  pills(String  of)  {                return  this        }        ...}

10

Page 19: Whats new in Groovy 2.0?

@glaforge

Command chains

//  variable  injectiondef  (of,  after,  hours)  =  /*...*/  //  implementing  the  DSL  logicdef  take(n)  {        [pills:  {  of  -­‐>                [chloroquinine:  {  after  -­‐>                        ['6':  {  time  -­‐>  }]                }]        }]}

//  -­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐-­‐take  2  pills  of  chloroquinine  after  6  hours

{ }

11

Page 20: Whats new in Groovy 2.0?

@glaforge

Command chains

12

Page 21: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)

12

Page 22: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

12

Page 23: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuation

12

Page 24: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

12

Page 25: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structures

12

Page 26: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

12

Page 27: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parens

12

Page 28: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

12

Page 29: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  terms

12

Page 30: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

12

Page 31: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

       (            ).        (                      ).      (            )

12

Page 32: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

       (            ).        (                      ).      (            )

         (                              ).            (        )

12

Page 33: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

       (            ).        (                      ).      (            )

         (                              ).            (        )

         (    ).        (    ).        (    )

12

Page 34: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

       (            ).        (                      ).      (            )

         (                              ).            (        )

         (    ).        (    ).        (    )

           (      ).                .        (          )

12

Page 35: Whats new in Groovy 2.0?

@glaforge

Command chains

//  methods  with  multiple  arguments  (commas)take  coffee    with  sugar,  milk    and  liquor

//  leverage  named-­‐args  as  punctuationcheck  that:  margarita    tastes  good

//  closure  parameters  for  new  control  structuresgiven  {}    when  {}    then  {}

//  zero-­‐arg  methods  require  parensselect  all    unique()  from  names

//  possible  with  an  odd  number  of  termstake  3    cookies

       (            ).        (                      ).      (            )

         (                              ).            (        )

         (    ).        (    ).        (    )

           (      ).                .        (          )

       (  ).

12

Page 36: Whats new in Groovy 2.0?

@glaforge

Runtime performance improvements

• Significant runtime improvements for primitive type operations–classical Fibonacci example x13 faster!–closer to Java performance

• Some direct method calls on this

• More on performance later on

13

Page 37: Whats new in Groovy 2.0?

@glaforge

GPars bundled• GPars is bundled

in the Groovy distribution

• GPars covers a wide range of parallel and concurrent paradigms–actors, fork/join, map/filter/reduce, dataflow, agents–parallel arrays, executors, STM, and more...

• And you can use it from plain Java as well!

14

Page 38: Whats new in Groovy 2.0?

@glaforge

Closure enhancements• Closure annotation parameters

• Some more functional flavor–composition

• compose several closures into one single closure

–trampoline• avoid stack overflow errors for recursive algorithms

–memoization• remember the outcome of previous closure invocations

• Currying improvements

15

Page 39: Whats new in Groovy 2.0?

@glaforge

Closure annotation parameters

16

@Retention(RetentionPolicy.RUNTIME)@interface  Invariant  {                Class  value()  //  a  closure  class}  @Invariant({  number  >=  0  })class  Distance  {                float  number                String  unit}    def  d  =  new  Distance(number:  10,  unit:  "meters")  def  anno  =  Distance.getAnnotation(Invariant)def  check  =  anno.value().newInstance(d,  d)assert  check(d)

{

Page 40: Whats new in Groovy 2.0?

@glaforge

Closure annotation parameters

16

@Retention(RetentionPolicy.RUNTIME)@interface  Invariant  {                Class  value()  //  a  closure  class}  @Invariant({  number  >=  0  })class  Distance  {                float  number                String  unit}    def  d  =  new  Distance(number:  10,  unit:  "meters")  def  anno  =  Distance.getAnnotation(Invariant)def  check  =  anno.value().newInstance(d,  d)assert  check(d)

{Poor-man’s GContracts

Page 41: Whats new in Groovy 2.0?

@glaforge

Builtin JSON support

• Consuming

• Producing

• Pretty-printing

17

Page 42: Whats new in Groovy 2.0?

@glaforge

Builtin JSON support

18

import  groovy.json.*  

def  payload  =  new  URL(        "http://github.../json/commits/...").text  

def  slurper  =  new  JsonSlurper()def  doc  =  slurper.parseText(payload)  

doc.commits.message.each  {  println  it  }

Page 43: Whats new in Groovy 2.0?

@glaforge

Builtin JSON support

19

import  groovy.json.*    def  json  =  new  JsonBuilder()    json.person  {                name  "Guillaume"        age  34                pets  "Hector",  "Felix"}  println  json.toString()

Page 44: Whats new in Groovy 2.0?

@glaforge

Builtin JSON support

19

import  groovy.json.*    def  json  =  new  JsonBuilder()    json.person  {                name  "Guillaume"        age  34                pets  "Hector",  "Felix"}  println  json.toString()

{                "person":  {                                "name":  "Guillaume",                                "age":  34,                                "pets":  [                                                "Hector",                                                "Felix"                                ]                }}

Page 45: Whats new in Groovy 2.0?

@glaforge

Builtin JSON support

20

import  groovy.json.*    println  JsonOutput.prettyPrint(        '''{"person":{"name":"Guillaume","age":34,'''  +          '''"pets":["Hector","Felix"]}}''')  

{                "person":  {                                "name":  "Guillaume",                                "age":  34,                                "pets":  [                                                "Hector",                                                "Felix"                                ]                }}

Page 46: Whats new in Groovy 2.0?

@glaforge

New AST transformations• @Log

• @Field

• @AutoClone• @AutoExternalizable

• @Canonical– @ToString, – @EqualsAndHashCode, – @TupleConstructor

• Controlling the execution of your code– @ThreadInterrupt, – @TimedInterrupt, – @ConditionalInterrupt

• @InheritConstructor

• @WithReadLock• @WithWriteLock

• @ListenerList

21

Page 47: Whats new in Groovy 2.0?

@glaforge

@Log

• Four different loggers can be injected–@Log, @Commons, @Log4j, @Slf4j

• Possible to implement your own strategy

22

import  groovy.util.logging.*    @Logclass  Car  {                Car()  {                                log.info  'Car  constructed'                }}    def  c  =  new  Car()

Page 48: Whats new in Groovy 2.0?

@glaforge

@Log

• Four different loggers can be injected–@Log, @Commons, @Log4j, @Slf4j

• Possible to implement your own strategy

22

import  groovy.util.logging.*    @Logclass  Car  {                Car()  {                                log.info  'Car  constructed'                }}    def  c  =  new  Car()

Guardedw/ an if

Page 49: Whats new in Groovy 2.0?

@glaforge

• Your application may run user’s code–what if the code runs in infinite loops or for too long?–what if the code consumes too many resources?

23

Controlling code execution

Page 50: Whats new in Groovy 2.0?

@glaforge

• Your application may run user’s code–what if the code runs in infinite loops or for too long?–what if the code consumes too many resources?

23

Controlling code execution

Page 51: Whats new in Groovy 2.0?

@glaforge

• Your application may run user’s code–what if the code runs in infinite loops or for too long?–what if the code consumes too many resources?

• 3 new transforms at your rescue–@ThreadInterrupt: adds Thread#isInterrupted checks

so your executing thread stops when interrupted–@TimedInterrupt: adds checks in method and closure

bodies to verify it’s run longer than expected–@ConditionalInterrupt: adds checks with your own

conditional logic to break out from the user code

23

Controlling code execution

Page 52: Whats new in Groovy 2.0?

@glaforge

@ThreadInterrupt

24

@ThreadInterruptimport  groovy.transform.ThreadInterrupt    while  (true)  {

       //  eat  lots  of  CPU}

33

Page 53: Whats new in Groovy 2.0?

@glaforge

@ThreadInterrupt

24

@ThreadInterruptimport  groovy.transform.ThreadInterrupt    while  (true)  {

       //  eat  lots  of  CPU}

 

       if  (Thread.currentThread.isInterrupted())                throw  new  InterruptedException(){ }

33

Page 54: Whats new in Groovy 2.0?

@glaforge

@ThreadInterrupt

• Two optional annotation parameters available–checkOnMethodStart (true by default)–applyToAllClasses (true by default)

24

@ThreadInterruptimport  groovy.transform.ThreadInterrupt    while  (true)  {

       //  eat  lots  of  CPU}

 

       if  (Thread.currentThread.isInterrupted())                throw  new  InterruptedException(){ }

33

Page 55: Whats new in Groovy 2.0?

@glaforge

@ToString• Provides a default toString() method to your types• Available annotation options

– includeNames, includeFields, includeSuper, excludes

25

import  groovy.transform.ToString    @ToStringclass  Person  {                String  name                int  age}    println  new  Person(name:  'Pete',  age:  15)//  =>  Person(Pete,  15)

Page 56: Whats new in Groovy 2.0?

@glaforge

@EqualsAndHashCode

• Provides default implementations for equals() and hashCode() methods

26

import  groovy.transform.EqualsAndHashCode    @EqualsAndHashCodeclass  Coord  {                int  x,  y}    def  c1  =  new  Coord(x:  20,  y:  5)def  c2  =  new  Coord(x:  20,  y:  5)    assert  c1  ==  c2assert  c1.hashCode()  ==  c2.hashCode()

Page 57: Whats new in Groovy 2.0?

@glaforge

@TupleConstructor• Provides a «classical» constructor with all properties• Several annotation parameter options available

27

import  groovy.transform.TupleConstructor    @TupleConstructor  class  Person  {                String  name                int  age}    def  m  =  new  Person('Marion',  3)              assert  m.name  ==  'Marion'assert  m.age    ==  3

Page 58: Whats new in Groovy 2.0?

@glaforge

@Canonical

• One annotation to rule them all!–@Canonical mixes together

• @ToString• @EqualsAndHashCode• @TupleConstructor

• You can customize behavior by combining @Canonical and one of the other annotations

28

Page 59: Whats new in Groovy 2.0?

@glaforge

@InheritConstructors

• Classes like Exception are painful when extended, as all the base constructors should be replicated

29

class  CustomException  extends  Exception  {        CustomException()                                                {  super()              }        CustomException(String  msg)                            {  super(msg)        }        CustomException(String  msg,  Throwable  t)  {  super(msg,  t)  }        CustomException(Throwable  t)                          {  super(t)            }}

Page 60: Whats new in Groovy 2.0?

@glaforge

@InheritConstructors

• Classes like Exception are painful when extended, as all the base constructors should be replicated

29

class  CustomException  extends  Exception  {        CustomException()                                                {  super()              }        CustomException(String  msg)                            {  super(msg)        }        CustomException(String  msg,  Throwable  t)  {  super(msg,  t)  }        CustomException(Throwable  t)                          {  super(t)            }}

import  groovy.transform.*

@InheritConstructorsclass  CustomException  extends  Exception  {

}

Page 61: Whats new in Groovy 2.0?

@glaforge

Miscelanous• Compilation customizers • Java 7 diamond operator• Slashy and dollar slashy strings• New GDK methods• (G)String to Enum coercion• Customizing the Groovysh prompt• Executing remote scripts

30

Page 62: Whats new in Groovy 2.0?

@glaforge

Compilation customizers• Ability to apply some customization to the Groovy

compilation process

• Three available customizers–ImportCustomizer–ASTTransformationCustomizer–SecureASTCustomizer

• But you can implement your own

31

Page 63: Whats new in Groovy 2.0?

@glaforge

Imports customizer

32

def  configuration  =  new  CompilerConfiguration()  def  custo  =  new  ImportCustomizer()custo.addStaticStar(Math.name)configuration.addCompilationCustomizers(custo)    def  result  =  new  GroovyShell(configuration)                          //  import  static  java.lang.Math.*        .evaluate("  cos  PI/3  ")                            

Page 64: Whats new in Groovy 2.0?

@glaforge

Customizing the Groovysh prompt

33

Page 65: Whats new in Groovy 2.0?

What’s cookingfor 2.0?

Page 66: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 67: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 68: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 69: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 70: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 71: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 72: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 73: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

Page 74: Whats new in Groovy 2.0?

@glaforge

Groovy 2.0 roadmap• Java 7 alignements: Project Coin

–binary literals–underscore in literals–multicatch

• JDK 7: InvokeDynamic• Towards a more modular Groovy• Static type checking • Static compilation

35

End  of  April?

Page 75: Whats new in Groovy 2.0?

@glaforge

Java 7 / JDK 7

• Project Coin and InvokeDynamic

36

Page 76: Whats new in Groovy 2.0?

@glaforge

Binary literals

• We had decimal, octal and hexadecimal notations for number literals

• We can now use binary representations too

37

int  x  =  0b10101111assert  x  ==  175  byte  aByte  =  0b00100001assert  aByte  ==  33  int  anInt  =  0b1010000101000101assert  anInt  ==  41285

Page 77: Whats new in Groovy 2.0?

@glaforge

Underscore in literals

• Now we can also add underscores in number literals for more readability

38

long  creditCardNumber  =  1234_5678_9012_3456Llong  socialSecurityNumbers  =  999_99_9999Lfloat  monetaryAmount  =  12_345_132.12long  hexBytes  =  0xFF_EC_DE_5Elong  hexWords  =  0xFFEC_DE5Elong  maxLong  =  0x7fff_ffff_ffff_ffffLlong  alsoMaxLong  =  9_223_372_036_854_775_807Llong  bytes  =  0b11010010_01101001_10010100_10010010

Page 78: Whats new in Groovy 2.0?

@glaforge

Multicatch

• One block for multiple exception caught–rather than duplicating the block

39

try  {        /*  ...  */}  catch(IOException  |  NullPointerException  e)  {        /*  one  block  to  treat  2  exceptions  */}

Page 79: Whats new in Groovy 2.0?

@glaforge

InvokeDynamic• Groovy 2.0 supports JDK 7’s invokeDynamic

–compiler will have a flag for compiling against JDK 7–might use the invokeDynamic backport for < JDK 7

• Benefits–more runtime performance!

• at least as fast as current «dynamic» Groovy

–in the long run, will allow us to get rid of code!• call site caching, thanks to MethodHandles• metaclass registry, thanks to ClassValues• will let the JIT inline calls more easily

40

Page 80: Whats new in Groovy 2.0?

@glaforge

Groovy Modularity• Groovy’s «all» JAR weighs in at 4MB

• Nobody needs everything–Template engine, Ant scripting, Swing UI building...

• Provide a smaller core–and several smaller JARs per feature

• Provide hooks for setting up DGM methods, etc.

41

Page 81: Whats new in Groovy 2.0?

@glaforge

Static Type Checking• Goal: make the Groovy compiler «grumpy»!

–and throw compilation errors (not at runtime)• Not everybody needs dynamic features all the time

–think Java libraries scripting• Grumpy should...

–tell you about your method or variable typos–complain if you call methods that don’t exist–shout on assignments of wrong types–infer the types of your variables–figure out GDK methods–etc...

42

Page 82: Whats new in Groovy 2.0?

@glaforge

Typos in your variable or method

43

import  groovy.transform.TypeChecked  void  method()  {}  @TypeChecked  test()  {        //  Cannot  find  matching  method  metthhoood()        metthhoood()          def  name  =  "Guillaume"        //  variable  naamme  is  undeclared        println  naamme}

Page 83: Whats new in Groovy 2.0?

@glaforge

Typos in your variable or method

43

import  groovy.transform.TypeChecked  void  method()  {}  @TypeChecked  test()  {        //  Cannot  find  matching  method  metthhoood()        metthhoood()          def  name  =  "Guillaume"        //  variable  naamme  is  undeclared        println  naamme}

Compilationerrors!

Page 84: Whats new in Groovy 2.0?

@glaforge

Typos in your variable or method

43

import  groovy.transform.TypeChecked  void  method()  {}  @TypeChecked  test()  {        //  Cannot  find  matching  method  metthhoood()        metthhoood()          def  name  =  "Guillaume"        //  variable  naamme  is  undeclared        println  naamme}

Compilationerrors!

Annotation can be atclass or method level

Page 85: Whats new in Groovy 2.0?

@glaforge

Complain on wrong assignments

44

//  cannot  assign  value  of  type...  to  variable...int  x  =  new  Object()Set  set  =  new  Object()  def  o  =  new  Object()int  x  =  o  String[]  strings  =  ['a','b','c']int  str  =  strings[0]  //  cannot  find  matching  method  plus()int  i  =  0i  +=  '1'

Page 86: Whats new in Groovy 2.0?

@glaforge

Complain on wrong assignments

44

//  cannot  assign  value  of  type...  to  variable...int  x  =  new  Object()Set  set  =  new  Object()  def  o  =  new  Object()int  x  =  o  String[]  strings  =  ['a','b','c']int  str  =  strings[0]  //  cannot  find  matching  method  plus()int  i  =  0i  +=  '1'

Compilationerrors!

Page 87: Whats new in Groovy 2.0?

@glaforge

Complain on wrong return types

45

//  checks  if/else  branch  return  valuesint  method()  {        if  (true)  {  'String'  }        else  {  42  }}//  works  for  switch/case  &  try/catch/finally  //  transparent  toString()  impliedString  greeting(String  name)  {        def  sb  =  new  StringBuilder()        sb  <<  "Hi  "  <<  name}

Page 88: Whats new in Groovy 2.0?

@glaforge

Complain on wrong return types

45

//  checks  if/else  branch  return  valuesint  method()  {        if  (true)  {  'String'  }        else  {  42  }}//  works  for  switch/case  &  try/catch/finally  //  transparent  toString()  impliedString  greeting(String  name)  {        def  sb  =  new  StringBuilder()        sb  <<  "Hi  "  <<  name}

Compilationerror!

Page 89: Whats new in Groovy 2.0?

@glaforge

Type inference

46

@TypeChecked  test()  {        def  name  =  "    Guillaume    "          //  String  type  infered  (even  inside  GString)        println  "NAME  =  ${name.toUpperCase()}"            //  Groovy  GDK  method  support        //  (GDK  operator  overloading  too)        println  name.trim()          int[]  numbers  =  [1,  2,  3]        //  Element  n  is  an  int        for  (int  n  in  numbers)  {                println  n        }}

Page 90: Whats new in Groovy 2.0?

@glaforge

Staticly checked & dyn. methods

47

@TypeCheckedString  greeting(String  name)  {        //  call  method  with  dynamic  behavior        //  but  with  proper  signature        generateMarkup(name.toUpperCase())}  //  usual  dynamic  behaviorString  generateMarkup(String  name)  {        def  sw  =  new  StringWriter()        new  MarkupBuilder(sw).html  {                body  {                        div  name                }        }        sw.toString()}

Page 91: Whats new in Groovy 2.0?

@glaforge

Instanceof checks

48

@TypeChecked  void  test(Object  val)  {

       if  (val  instanceof  String)  {                println  val.toUpperCase()        }  else  if  (val  instanceof  Number)  {                println  "X"  *  val.intValue()        }

}

Page 92: Whats new in Groovy 2.0?

@glaforge

Instanceof checks

48

@TypeChecked  void  test(Object  val)  {

       if  (val  instanceof  String)  {                println  val.toUpperCase()        }  else  if  (val  instanceof  Number)  {                println  "X"  *  val.intValue()        }

}

No needfor casts

Page 93: Whats new in Groovy 2.0?

@glaforge

Instanceof checks

48

@TypeChecked  void  test(Object  val)  {

       if  (val  instanceof  String)  {                println  val.toUpperCase()        }  else  if  (val  instanceof  Number)  {                println  "X"  *  val.intValue()        }

}

No needfor casts

Can call String#multiply(int)from the Groovy Development Kit

Page 94: Whats new in Groovy 2.0?

@glaforge

Lowest Upper Bound• Represents the lowest «super» type classes have

in common–may be virtual (aka «non-denotable»)

49

@TypeChecked  test()  {        //  an  integer  and  a  BigDecimal        return  [1234,  3.14]}

Page 95: Whats new in Groovy 2.0?

@glaforge

Lowest Upper Bound• Represents the lowest «super» type classes have

in common–may be virtual (aka «non-denotable»)

49

@TypeChecked  test()  {        //  an  integer  and  a  BigDecimal        return  [1234,  3.14]}

Inferred return type:List<Number>

Page 96: Whats new in Groovy 2.0?

@glaforge

Flow typing• Static type checking shouldn’t complain even for

bad coding practicies which work w/o type checks

50

@TypeChecked  test()  {        def  var  =  123                  //  inferred  type  is  int        int  x  =  var                      //  var  is  an  int        var  =  "123"                      //  assign  var  with  a  String

       x  =  var.toInteger()      //  no  problem,  no  need  to  cast

       var  =  123        x  =  var.toUpperCase()  //  error,  var  is  int!}

Page 97: Whats new in Groovy 2.0?

@glaforge

Gotchas: static checking vs dynamic• Type checking works at compile-time

–adding @TypeChecked doesn’t change behavior• do not confuse with static compilation

• Most dynamic features cannot be type checked–metaclass changes, categories–dynamically bound variables (ex: script’s binding)

• However, compile-time metaprogramming works–as long as proper type information is defined

51

Page 98: Whats new in Groovy 2.0?

@glaforge

Gotchas: runtime metaprogramming

52

@TypeChecked  void  test()  {        Integer.metaClass.foo  =  {}        123.foo()}

Page 99: Whats new in Groovy 2.0?

@glaforge

Gotchas: runtime metaprogramming

52

@TypeChecked  void  test()  {        Integer.metaClass.foo  =  {}        123.foo()}

Not allowed:metaClass property

is dynamic

Page 100: Whats new in Groovy 2.0?

@glaforge

Gotchas: runtime metaprogramming

52

@TypeChecked  void  test()  {        Integer.metaClass.foo  =  {}        123.foo()}

Not allowed:metaClass property

is dynamic

Method notrecognized

Page 101: Whats new in Groovy 2.0?

@glaforge

Gotchas: closures need explicit types

• A «Groovy Enhancement Proposal» to address this issue

53

@TypeChecked  test()  {        ["a",  "b",  "c"].collect  {                it.toUpperCase()  //  Not  OK        }}

Page 102: Whats new in Groovy 2.0?

@glaforge

Gotchas: closures need explicit types

• A «Groovy Enhancement Proposal» to address this issue

53

@TypeChecked  test()  {        ["a",  "b",  "c"].collect  {  String  it  -­‐>                it.toUpperCase()  //  OK,  it’s  a  String        }}

Page 103: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

54

@TypeChecked  test()  {        def  var  =  "abc"                      def  cl  =  {  var  =  new  Date()  }        cl()        var.toUpperCase()    //  Not  OK!}

Page 104: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

54

@TypeChecked  test()  {        def  var  =  "abc"                      def  cl  =  {  var  =  new  Date()  }        cl()        var.toUpperCase()    //  Not  OK!}

var assigned in the closure:«shared closure variable»

Page 105: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

54

@TypeChecked  test()  {        def  var  =  "abc"                      def  cl  =  {  var  =  new  Date()  }        cl()        var.toUpperCase()    //  Not  OK!}

var assigned in the closure:«shared closure variable»

Impossible to ensure the assignment really happens

Page 106: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

54

@TypeChecked  test()  {        def  var  =  "abc"                      def  cl  =  {  var  =  new  Date()  }        cl()        var.toUpperCase()    //  Not  OK!}

var assigned in the closure:«shared closure variable»

Impossible to ensure the assignment really happens

Only methods of the most specific compatible type (LUB)are allowed by the type checker

Page 107: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

55

class  A                      {  void  foo()  {}  }class  B  extends  A  {  void  bar()  {}  }

@TypeChecked  test()  {        def  var  =  new  A()        def  cl  =  {  var  =  new  B()  }        cl()        var.foo()      //  OK!}

Page 108: Whats new in Groovy 2.0?

@glaforge

Closure shared variables

55

class  A                      {  void  foo()  {}  }class  B  extends  A  {  void  bar()  {}  }

@TypeChecked  test()  {        def  var  =  new  A()        def  cl  =  {  var  =  new  B()  }        cl()        var.foo()      //  OK!}

var is at leastan instance of A

Page 109: Whats new in Groovy 2.0?

@glaforge

Static Compilation

• Given your Groovy code can be type checked...we can as well compile it «statically»

–ie. generate the same byte code as javac

56

Page 110: Whats new in Groovy 2.0?

@glaforge

Static Compilation: advantages• You gain:

–Type safety• thanks to static type checking

– static compilation builds upon static type checking

–Faster code• as close to Java’s performance as possible

–Code immune to «monkey patching»• metaprogramming badly used can interfere with framework code

–Smaller bytecode size

57

Page 111: Whats new in Groovy 2.0?

@glaforge

Static Compilation: disadvantages• But you loose:

–Dynamic features• metaclass changes, categories, etc.

–Dynamic method dispatch• although emulated as close as possible to «dynamic» Groovy

58

Page 112: Whats new in Groovy 2.0?

@glaforge

Staticly compiled & dyn. methods

59

@CompileStaticString  greeting(String  name)  {        //  call  method  with  dynamic  behavior        //  but  with  proper  signature        generateMarkup(name.toUpperCase())}  //  usual  dynamic  behaviorString  generateMarkup(String  name)  {        def  sw  =  new  StringWriter()        new  MarkupBuilder(sw).html  {                body  {                        div  name                }        }        sw.toString()}

Page 113: Whats new in Groovy 2.0?

@glaforge

What about performance?• Comparisons between:

–Java

–Groovy static compilation• ie. Groovy 2.0

–Groovy with primitive optimizations• ie. since Groovy 1.8

–Groovy without optimizations• ie. Groovy 1.7 and before

60

Page 114: Whats new in Groovy 2.0?

@glaforge

What about performance?

61

Fibonacci Pi  (π)  quadrature

Binarytrees

Java

StaMccompilaMon

PrimiMve  opMmizaMons

No  prim.opMmizaMons

140  ms 93  ms 4.5  s

150  ms 220  ms 7.6  s

270  ms 110  ms 29.6  s

3800  ms 3.8  s 50.0  s1.7

1.8

2.0

Page 115: Whats new in Groovy 2.0?

@glaforge

Summary• Main themes of the Groovy 2.0 release

–Modularity

–Embark the JDK 7 enhancements• Project Coin• Invoke Dynamic

–Static aspects• Static type checking• Static compilation

62

Page 116: Whats new in Groovy 2.0?

@glaforge

Summary

63

ROCKS!

Page 118: Whats new in Groovy 2.0?

Q&AGot questions,

really?

Page 119: Whats new in Groovy 2.0?

@glaforge

Image credits• Iceberg: http://hqworld.net/gallery/data/media/20/tip_of_the_iceberg.jpg

• Bicycle: http://drunkcyclist.com/gallery/main.php?g2_view=core.DownloadItem&g2_itemId=2131&g2_serialNumber=2

• Pills: http://www.we-ew.com/wp-content/uploads/2011/01/plan-b-pills.jpg

• Chains: http://2.bp.blogspot.com/-GXDVqUYSCa0/TVdBsON4tdI/AAAAAAAAAW4/EgJOUmAxB28/s1600/breaking-chains5_copy9611.jpg

• Cooking: http://www.flickr.com/photos/eole/449958332/sizes/l/

• Oui nide iou: http://desencyclopedie.wikia.com/wiki/Fichier:Superdupont_we_need_you.jpg

• Guitar: http://www.lelitteraire.com/IMG/breveon323.jpg

• Trampoline: http://www.fitness-online.fr/images/trampoline-1-m.jpg

• Curry: http://www.pot-a-epices.com/wp-content/uploads/2009/02/curry1.jpg

• Slurp: http://www.ohpacha.com/218-532-thickbox/gamelle-slurp.jpg

• Caution: http://www.jeunes-epinay-sur-seine.fr/wp-content/uploads/2010/11/caution-colocation.jpg

• Grumpy: http://mafeuilledechou.fr/__oneclick_uploads/2010/05/grumpy.jpg

• Modularity: http://php.jglobal.com/blog/wp-content/uploads/2009/11/modularity.jpg

• Agenda: http://www.plombiereslesbains.fr/images/stories/agenda.jpg

• Java 7: http://geeknizer.com/wp-content/uploads/java7.jpg

• WIP: http://www.connetport.com/wp-content/uploads/Work_in_progress.svg_.png

• Grumpy 2: http://grumpy.division-par-zero.fr/wp-content/images/grumpy.jpg

66