Slide 1

Slide 1 text

Groovy in 2014 & beyond Guillaume Laforge Groovy Project Manager http://glaforge.appspot.com @glaforge

Slide 2

Slide 2 text

No content

Slide 3

Slide 3 text

Stay up-to-date Groovy Weekly newsletter (Every Tuesday) http://beta.groovy-lang.org/groovy-weekly.html

Slide 4

Slide 4 text

Stay up-to-date Groovy Google+ page
 https://google.com/+groovy

Slide 5

Slide 5 text

Stay up-to-date Groovy Google+ community http://bit.ly/g-community

Slide 6

Slide 6 text

Agenda

Slide 7

Slide 7 text

The Groovy roadmap… 2015 2014 2013 Groovy 2.3 Groovy 2.4 Groovy 2.2 Groovy 2.5 ? Groovy 3.0 ?

Slide 8

Slide 8 text

Groovy 2.3 ! • JDK 8 runtime support • Traits • New and updates AST transformations • NIO2 module • JSON improvements & performance gains • New Markup template engine • Documentation overhaul

Slide 9

Slide 9 text

Groovy 2.4 ! • Android support ! • New website ! • Macro system? • New grammar?

Slide 10

Slide 10 text

Groovy 3.0 ! • New Meta-Object Protocol ! • Invoke-dynamic based runtime ! • Rewritten language grammar with Antlr v4 • unless re-scheduled for Groovy 2.4 if GSoC successful

Slide 11

Slide 11 text

@YourTwitterHandle #DVXFR14{session hashtag} Groovy 2.3

Slide 12

Slide 12 text

@YourTwitterHandle JDK 8 support

Slide 13

Slide 13 text

JDK 8 support — closures & lambdas IntStream.range(1,  100).forEach(s  -­‐>                                                System.out.println(s));   ! Files.lines(Paths.get('README.adoc'))            .map(it  -­‐>  it.toUpperCase())            .forEach(it  -­‐>  System.out.println(it)); IntStream.range(1,  100).forEach  {  println  it  }   ! Files.lines(Paths.get('README.adoc'))            .map  {  it.toUpperCase()  }            .forEach  {  println  it  } Use Groovy closures wherever you pass lambdas in Java 8

Slide 14

Slide 14 text

@YourTwitterHandle Traits

Slide 15

Slide 15 text

Traits • Like interfaces, but with method bodies • similar to Java 8 interface default methods • Elegant way to compose behavior • multiple inheritance, without the « diamond problem » • Traits can also be stateful • traits can have properties like normal classes • Compatible with static typing & compilation • class methods coming from traits are also visible from Java • Also possible to implement traits at runtime

Slide 16

Slide 16 text

trait  FlyingAbility  {          String  fly()  {  "I'm  flying!"  }   }   ! class  Bird  implements  FlyingAbility  {}   def  b  =  new  Bird()   ! assert  b.fly()  ==  "I'm  flying!" Traits: a simple example « trait », a new keyword for a new concept a class 
 « implements »
 a trait the fly() method from the trait is available

Slide 17

Slide 17 text

trait  Named  {          String  name   }   ! class  Bird  implements  Named  {}   def  b  =  new  Bird(name:  'Colibri')   ! assert  b.name  ==  'Colibri' Traits: stateful a Groovy property implement the trait Groovy named argument constructor access the property

Slide 18

Slide 18 text

trait  Named  {  String  name  }   ! trait  FlyingAbility  extends  Named  {          String  fly()  {  "I'm  a  flying  ${name}!"  }   }   ! class  Bird  implements  FlyingAbility  {}   def  b  =  new  Bird(name:  'Colibri')   ! assert  b.name  ==  'Colibri'   assert  b.fly()  ==  "I'm  a  flying  Colibri!" Traits: inheritance extend the Named trait access the name property implement the composite trait

Slide 19

Slide 19 text

trait  FlyingAbility  {          String  fly()  {  "I'm  a  flying  $name!"  }   }   ! trait  Named  {  String  name  }   ! class  Bird  implements  Named,  FlyingAbility  {}   def  b  =  new  Bird(name:  'Colibri')   ! assert  b.name  ==  'Colibri'   assert  b.fly()  ==  "I'm  a  flying  Colibri!" Traits: multiple inheritance (+dyn.) access a dynamic property implements two traits! dynamic ‘name’ property interpolated

Slide 20

Slide 20 text

trait  KiteSurfer  {  String  surf()  {  'kite'  }  }   ! trait  WebSurfer    {  String  surf()  {    'web'  }  }   ! class  Person  {  String  name  }   ! class  Hipster  extends  Person                        implements  KiteSurfer,  WebSurfer  {}   ! def  h  =  new  Hipster()   assert  h.surf()  ==  'web' Traits: what about conflicts? two surf() methods extending a class and implementing the two traits last declared trait wins!

Slide 21

Slide 21 text

trait  KiteSurfer  {  String  surf()  {  'kite'  }  }   ! trait  WebSurfer    {  String  surf()  {    'web'  }  }   ! class  Person  {  String  name  }   ! class  Hipster  extends  Person                        implements  WebSurfer,  KiteSurfer  {}   ! def  h  =  new  Hipster()   assert  h.surf()  ==  'kite' Traits: what about conflicts? reverse the order!

Slide 22

Slide 22 text

trait  KiteSurfer  {  String  surf()  {  'kite'  }  }   ! trait  WebSurfer    {  String  surf()  {    'web'  }  }   ! class  Person  {  String  name  }   ! class  Hipster  extends  Person                        implements  WebSurfer,  KiteSurfer  {          String  surf()  {  KiteSurfer.super.surf()  }   }   ! def  h  =  new  Hipster()   assert  h.surf()  ==  'kite' Traits: what about conflicts? Be explicit! Override surf() 
 & use ‘super’ Your class method takes precedence over the traits

Slide 23

Slide 23 text

trait  Named  {          String  name   }   ! class  Animal  {}   class  NamedAnimal  implements  Named  {}   ! def  na  =  new  NamedAnimal(name:  'Felix')   ! assert  na.name  ==  'Felix' Traits: runtime implementation Somewhat artificial to have to create an intermediary class to get named animals

Slide 24

Slide 24 text

trait  Named  {          String  name   }   ! class  Animal  {}   ! ! def  na  =  new  Animal()  as  Named   na.name  =  'Felix'   assert  na.name  ==  'Felix' Traits: runtime implementation Runtime trait, 
 with Groovy’s usual coercion mechanism

Slide 25

Slide 25 text

trait  Named  {  String  name  }   ! trait  Quacks  {          String  quack()  {  'Quack!'  }   }   ! class  Animal  {}   ! def  na  =  new  Animal().withTraits  Named,  Quacks   na.name  =  'Daffy'   assert  na.name  ==  'Daffy'   assert  na.quack()  ==  'Quack!' Traits: runtime implementation Implement several traits at once, at runtime

Slide 26

Slide 26 text

Traits: miscellaneous • Traits can… ! • have private fields and methods • have abstract methods • implement interfaces • extend other traits or implement several traits • be statically type checked and compiled

Slide 27

Slide 27 text

@YourTwitterHandle AST transforms

Slide 28

Slide 28 text

New: @TailRecursive import  groovy.transform.TailRecursive   ! @TailRecursive   def  fact(BigInteger  n,  accu  =  1G)  {          if  (n  <  2)  accu          else  fact(n  -­‐  1,  n  *  accu)   }   ! assert  fact(1000)  >  10e2566 Rewrites tail recursive friendly function serially Doesn’t blow up with a stack overflow error Downside of tail recursion is 
 you might have to rewrite 
 your algo to be tailrec friendly

Slide 29

Slide 29 text

New: @Sortable import  groovy.transform.*   ! @Sortable   class  Person  {          String  lastName          String  firstName          int  age   } Makes the class Comparable by multiple Comparators First compare by lastName, then by firstName, etc. You can also specify ‘includes’ / ‘excludes’ properties

Slide 30

Slide 30 text

@BaseScript improvements abstract  class  CustomBase  extends  Script  {          int  meaningOfLife  =  42   } @BaseScript(CustomBase)   import  groovy.transform.BaseScript   ! assert  meaningOfLife  ==  42 You can add your own base methods and properties to all compiled scripts Define the base script class for this script Ability to put the annotation on imports & package

Slide 31

Slide 31 text

@BaseScript custom abstract method abstract  class  CustomBase  extends  Script  {      def  run()  {          before()          internalRun()          after()      }   !    abstract  internalRun()   !    def  before()  {  println  'before'  }      def  after()    {  println  'after'    }   } import  groovy.transform.BaseScript   @BaseScript  CustomBase  script   ! println  'Hello' You can define your own abstract method for script bodies

Slide 32

Slide 32 text

@YourTwitterHandle NIO2 module

Slide 33

Slide 33 text

JDK 7+ NIO2 module • All the familiar methods on File 
 retrofitted on Path as well path.withReader  {  Reader  r  -­‐>  ...  }   path.eachLine  {  String  line  -­‐>  ...  }   path.eachFileRecurse  {  Path  p  -­‐>  ...  }   path  <<  'some  content'   path  <<  bytes   path.readLines()   … Feature request to add all the java.nio.file.Files static utility methods as GDK

Slide 34

Slide 34 text

@YourTwitterHandle JSON

Slide 35

Slide 35 text

JSON parser / builder perf. increase • Re-implementation of JSON support 
 for speed & efficiency • parser forked off the Boon JSON project • serializer carefully fine-tuned ! • Article on the parsing speed improvements • http://rick-hightower.blogspot.fr/2014/04/groovy-and-boon-provide-fastest-json.html Benchmark gives 3x to 4x performance factor 
 over Jackson and GSON

Slide 36

Slide 36 text

New modes for parsing • Original JsonSlurper renamed to JsonSlurperClassic ! • Additional parsing modes: • INDEX_OVERLAY: super fast for <2MB payloads • using a « parsing overlay » technique • CHARACTER_SOURCE: for >2MB payloads • implemented with sliding windows over readers • LAX: beyond the JSON spec, nice for configuration files • support single quotes, / and # comments • CHAR_BUFFER: general purpose

Slide 37

Slide 37 text

JsonSlurper for configuration files import  groovy.json.*   import  static  groovy.json.JsonParserType.*   ! def  parser  =  new  JsonSlurper().setType(LAX)   ! def  conf  =  parser.parseText  '''          //  configuration  file          {                  //  no  quote  for  key,  single  quoted  value                  environment:  'production'                  #  pound-­‐style  comment                  'server':  5          }   '''   ! assert  conf.environment  ==  'production'   assert  conf.server  ==  5 More tolerant parser: 
 single quotes, 
 non-quoted keys, 
 // and # comments, missing comas

Slide 38

Slide 38 text

@YourTwitterHandle Markup template engine >

Slide 39

Slide 39 text

Markup template engine • Based on the principles of Groovy’s « builders » • and particularly the MarkupBuilder class
 for generating arbitrary XML / HTML payloads • Compiled statically for fast template rendering • Internationalization aware •provide the desired Locale in the configuration object •usual suffix notation template_fr_FR.tpl • Custom base template class •ability to provide reusable methods across your templates

Slide 40

Slide 40 text

Markup template engine — the idea cars  {        cars.each  {                car(make:  it.make,  name:  it.name)        }   } model = [cars: [! new Car(make: 'Peugeot', name: '508'), ! new Car(make: 'Toyota', name: 'Prius’)! ]] ! ! ! Your template Feed a model into your template Generate the XML output

Slide 41

Slide 41 text

Markup template engine — in action import  groovy.text.markup.*   ! def  config  =  new  TemplateConfiguration()   def  engine  =  new  MarkupTemplateEngine(config)   def  tmpl  =  engine.createTemplate('''          p("Hello  ${model.name}")   ''')   def  model  =  [name:  'World']   System.out  <<  tmpl.make(model)

Slide 42

Slide 42 text

Markup template engine — includes //  include  another  template   include  template:  'foo.tpl'           //  include  raw  content   include  unescaped:  'raw.txt'   ! //  escape  &  include   include  escaped:  'to_escape.txt'

Slide 43

Slide 43 text

Markup template engine //  escaped  automatically   yield  'some  raw  content'   ! //  include  raw  content   yieldUnescaped  'content'   ! //     xmlDeclaration()                 //     comment  'comment'                 ! //  adds  new  lines   newLine()                                 ! //  process.  instruct.   pi(/*  ...  */)                      

Slide 44

Slide 44 text

Markup template engine ! • Configuration options ! • declaration encoding ! • expand empty elements ! • use double quotes ! • newline string ! ! ! ! ! ! ! • auto escape ! • auto indent ! • base template class ! • locale

Slide 45

Slide 45 text

Markup template engine — static! • Type-checked templates available • use createTypeCheckedModelTemplate() 
 instead of createTemplate() • Advantages • get compilation errors • if a variable is not available • if you make mistakes in the code snippets • even faster templates

Slide 46

Slide 46 text

Markup template engine — static! • With typed check model creation method ! ! ! ! • Or declare your model types in the template def  modelTypes  =  [cars:  "List"]   ! def  tmpl  =  engine.      createTypeCheckedModelTemplate(
            "page.tpl",  modelTypes) modelTypes  =  {          List  cars   }   ! cars.each  {  car  -­‐>          p("Car  name:  $car.name")   } Works with createTemplate() too

Slide 47

Slide 47 text

@YourTwitterHandle Documentation overhaul

Slide 48

Slide 48 text

GroovyDoc

Slide 49

Slide 49 text

Groovy GDK documentation

Slide 50

Slide 50 text

Brand new documentation

Slide 51

Slide 51 text

@YourTwitterHandle #DVXFR14{session hashtag} Groovy 2.4

Slide 52

Slide 52 text

Beta groovy-lang.org website Notice the « improve this doc » button!

Slide 53

Slide 53 text

Android support • You can use Groovy to 
 code Android apps! • use Groovy 2.4.0-beta-1 • prefer @CompileStatic ! • Two great posts to get started: • http://melix.github.io/blog/2014/06/ grooid.html • http://melix.github.io/blog/2014/06/ grooid2.html

Slide 54

Slide 54 text

Android support Source code available: https://github.com/melix/gr8confagenda

Slide 55

Slide 55 text

Groovy Macros ! • Sergei Egorov wants to contribute a macro module • https://github.com/groovy/groovy-core/pull/470 ! • Simplify creation of AST transformations • less boilerplate manipulating the Groovy AST API • more powerful and less limited than AstBuilder

Slide 56

Slide 56 text

Groovy Macros ! • Authoring AST transformations can be verbose: def  someVariable  =  new  ConstantExpression("xyz")   def  returnStatement  =  new  ReturnStatement(          new  ConstructorCallExpression(                  ClassHelper.make(SomeCoolClass),                  new  ArgumentListExpression(someVariable)          )   )

Slide 57

Slide 57 text

Groovy Macros • With Groovy Macros, it could be simpler: def  someVariable  =  macro  {  "xyz"  }   def  returnStatement  =  macro  {            new  SomeCoolClass($v{  someVariable  })     } Special « macro » command Quasi-quotation

Slide 58

Slide 58 text

@YourTwitterHandle #DVXFR14{session hashtag} Groovy 3.0

Slide 59

Slide 59 text

No content

Slide 60

Slide 60 text

@YourTwitterHandle MOP 2

Slide 61

Slide 61 text

Goals for the new MOP • Leverage & build upon JDK 7+ invoke dynamic • get Java-like performance even for dynamic code • Rationalize the sedimentation of meta- programming • more coherence, less corner cases & inconsistencies • Provide a notion of « realm » • shield users of « monkey patching » • finer-grained control of meta-programming reach • Private visibility anyone?

Slide 62

Slide 62 text

@YourTwitterHandle Antlr v4 Grammar

Slide 63

Slide 63 text

Antlr v4 grammar • Problems • Groovy still uses Antlr v2! • but version 3 and 4 are out • Groovy’s grammar evolved from a Java grammar • harder to fix and evolve, especially with Antlr v2 • Advantages • Start from a clean slate • Antlr 4 more tolerant 
 and powerful regarding ambiguities • Time to clean some grammar & syntax warts! • Need to implement the Java 8 constructs! A « Google Summer of Code » student is currently helping

Slide 64

Slide 64 text

@YourTwitterHandle Java 8 support

Slide 65

Slide 65 text

Java 8 support • Additional grammar & semantic features to support • to keep saying Groovy / Java interoperability is awesome! • New in Java 8 • lambdas • method references • default methods in interfaces • stream API, date / time API • annotations on types & repeated annotations Groovy had already: closures, method pointers, mixins, enriched collection & time APIs

Slide 66

Slide 66 text

@YourTwitterHandle #DVXFR14{session hashtag} Summary

Slide 67

Slide 67 text

Groovy rocks the JVM 
 since 2003!

Slide 68

Slide 68 text

@YourTwitterHandle #DVXFR14{session hashtag} Q & A

Slide 69

Slide 69 text

Image credits • Rue pavée — By-Nc-Sa • http://www.flickr.com/photos/22914687@N05/4957591422/sizes/l/ • Sous la Tour Eiffel — By-Nc-Sa • http://www.flickr.com/photos/stewiedewie/244850735/sizes/l/in/photostream/ • Sous le pont — By-Nc-Nd • http://www.landscape-photo.net/displayimage.php?pid=5194 • Paris Metro - By-Nc-Sa • http://www.flickr.com/photos/22914687@N05/6317047263/sizes/l/ • Big rock • http://wallpaper.preview-reviews.com/12852-red-rocks-in-a-snowstorm • Android robot • http://crackberry.com/sites/crackberry.com/files/styles/large/public/topic_images/2013/ANDROID.png? itok=xhm7jaxS • Modern MOP • http://i933.photobucket.com/albums/ad179/autobin/Wonder%20Mop/wondermop4.jpg • Jason • http://static.comicvine.com/uploads/original/3/32405/1031312-jason_19_inch_figure_l.jpg • Jigsaw • http://www.psdgraphics.com/file/psd-jigsaw-icon.jpg