• Like

Loading…

Flash Player 9 (or above) is needed to view presentations.
We have detected that you do not have it on your computer. To install it, go here.

Groovy to infinity and beyond - SpringOne2GX - 2010 - Guillaume Laforge

  • 2,260 views
Uploaded on

 

More in: Technology
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Be the first to comment
No Downloads

Views

Total Views
2,260
On Slideshare
0
From Embeds
0
Number of Embeds
1

Actions

Shares
Downloads
47
Comments
0
Likes
3

Embeds 0

No embeds

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
    No notes for slide

Transcript

  • 1. Chicago, October 19 - 22, 2010 to Infinity and Beyond! Guillaume Laforge — SpringSource jeudi 21 octobre 2010
  • 2. to Infinity and Beyond jeudi 21 octobre 2010
  • 3. Guillaume Laforge • Groovy Project Manager • JSR-241 Spec Lead • Head of Groovy Development at SpringSource • Initiator of the Grails framework • Founder of the Gaelyk toolkit • Co-author of Groovy in Action • Speaker: JavaOne, QCon, JavaZone, Sun TechDays, Devoxx, The Spring Experience, SpringOne2GX, JAX, Dynamic Language World, IJTC, and more... 3 jeudi 21 octobre 2010
  • 4. Bug killer... real insects with legs! • Thanks to Groovy, with one hand left for coding, I’m still more productive than with Java! 4 jeudi 21 octobre 2010
  • 5. Bug killer... real insects with legs! • Thanks to Groovy, with one hand left for coding, I’m still more productive than with Java! 4 jeudi 21 octobre 2010
  • 6. Agenda SpringOne 2GX 2010. All rights reserved. Do not distribute without permission. jeudi 21 octobre 2010
  • 7. Agenda • Past – Groovy 1.6 flashback • Present – Groovy 1.7 novelties – A few Groovy 1.7.x refinements • Future – What’s cooking for 1.8 and beyond 6 jeudi 21 octobre 2010
  • 8. looking into the Past jeudi 21 octobre 2010
  • 9. Big highlights of Groovy 1.6 • Greater compile-time and runtime performance • Multiple assignments • Optional return for if/else and try/catch/finally • Java 5 annotation definition • AST Transformations • The Grape module and dependency system • Various Swing related improvements • JMX Builder • Metaprogramming additions • JSR-223 scripting engine built-in • Out-of-the-box OSGi support 8 jeudi 21 octobre 2010
  • 10. Multiple assignement // multiple assignment def (a, b) = [1, 2] assert a == 1 && b == 2 // with typed variables def (int c, String d) = [3, "Hi"] assert c == 3 && d == "Hi" def geocode(String place) { [48.8, 2.3] } def lat, lng // assignment to existing variables (lat, lng) = geocode('Paris') // classical variable swaping example (a, b) = [b, a] 9 jeudi 21 octobre 2010
  • 11. More optional return // optional return for if statements def m1() {     if (true) 1     else 0 } assert m1() == 1 // optional return for try/catch/finally def m2(bool) {     try {         if (bool) throw new Exception()         1     } catch (any) { 2 }     finally { 3 } } assert m2(true) == 2 && m2(false) == 1 10 jeudi 21 octobre 2010
  • 12. AST Transformation (1/2) • Groovy 1.6 introduced AST Transformations • AST: Abstract Syntax Tree • Ability to change what’s being compiled by the Groovy compiler... at compile time – No runtime impact! – Change the semantics of your programs! Even hijack the Groovy syntax! – Implementing recurring patterns in your code base – Remove boiler-plate code • Two kinds: global and local (triggered by anno) 11 jeudi 21 octobre 2010
  • 13. AST Transformations (2/2) • Transformations introduced in 1.6 – @Singleton – @Immutable, @Lazy, @Delegate – @Newify – @Category, @Mixin – @PackageScope – Swing’s @Bindable and @Vetoable – Grape’s own @Grab 12 jeudi 21 octobre 2010
  • 14. @Immutable • To properly implement immutable classes – No mutations — state musn’t change – Private final fields – Defensive copying of mutable components – Proper equals() / hashCode() / toString() for comparisons or fas keys in maps @Immutable class Coordinates {     Double lat, lng } def c1 = new Coordinates(lat: 48.8, lng: 2.5) def c2 = new Coordinates(48.8, 2.5) assert c1 == c2 13 jeudi 21 octobre 2010
  • 15. Grab a grape! • Simple distribution and sharing of Groovy scripts • Dependencies stored locally – Can even use your own local repositories @Grab(group   = 'org.mortbay.jetty',       module  = 'jetty‐embedded',       version = '6.1.0') def startServer() {     def srv = new Server(8080) SIONS)     def ctx = new Context(srv , "/", SES     ctx.resourceBase = "." ovy")      ctx.addServlet(GroovyServlet, "*.gro     srv.start() } 14 jeudi 21 octobre 2010
  • 16. Metaprogramming additions (1/2) • ExpandoMetaClass DSL – factoring EMC changes Number.metaClass {     multiply { Amount amount ‐>          amount.times(delegate)      }     div { Amount amount ‐>          amount.inverse().times(delegate)      } } 15 jeudi 21 octobre 2010
  • 17. Metaprogramming additions (2/2) • Runtime mixins class FlyingAbility {     def fly() { "I'm ${name} and I fly!" } } class JamesBondVehicle {     String getName() { "James Bond's vehicle" } } JamesBondVehicle.mixin FlyingAbility assert new JamesBondVehicle().fly() ==     "I'm James Bond's vehicle and I fly!" 16 jeudi 21 octobre 2010
  • 18. JMX Builder • A DSL for handling JMX – in addition of Groovy MBean // Create a connector server def jmx = new JmxBuilder() jmx.connectorServer(port:9000).start() // Create a connector client jmx.connectorClient(port:9000).connect() //Export a bean jmx.export { bean new MyService() } // Defining a timer jmx.timer(name: "jmx.builder:type=Timer",      event: "heartbeat", period: "1s").start() // JMX listener jmx.listener(event: "someEvent", from: "bean",      call: { evt ‐> /* do something */ }) 17 jeudi 21 octobre 2010
  • 19. into the Present... jeudi 21 octobre 2010
  • 20. Big highlights of Groovy 1.7 • Anonymous Inner Classes and Nested Classes • Annotations anywhere • Grape improvements • Power Asserts • AST Viewer • AST Builder • Customize the Groovy Truth! • Rewrite of the GroovyScriptEngine • Groovy Console improvements • SQL support refinements 19 jeudi 21 octobre 2010
  • 21. AIC and NC • Anonymous Inner Classes and Nested Classes 20 jeudi 21 octobre 2010
  • 22. AIC and NC • Anonymous Inner Classes and Nested Classes Fo rJ ava ’n p aste c opy atib ility co mp sak e :-) 20 jeudi 21 octobre 2010
  • 23. Annonymous Inner Classes bo olean called = false Timer ti mer = new Timer() timer.schedule(n ew TimerTask() {     void run() {          called = true     } }, 0) sleep 100 assert called 21 jeudi 21 octobre 2010
  • 24. Annonymous Inner Classes bo olean called = false Timer ti mer = new Timer() timer.schedule(n ew TimerTask() {     void run() {          called = true     } { called = true } }, 0) as TimerTask sleep 100 assert called 21 jeudi 21 octobre 2010
  • 25. Nested Classes class Environment {     static class Production          extends Environment {}     static class Development          extends Environment {} } new Environment.Production() 22 jeudi 21 octobre 2010
  • 26. Anotations anywhere • You can now put annotations – on imports – on packages – on variable declarations • Examples with @Grab following... 23 jeudi 21 octobre 2010
  • 27. Grape improvements (1/4) • @Grab on import @Grab(group = 'net.sf.json‐lib',       module = 'json‐lib',      version = '2.3',  classifier = 'jdk15') import net.sf.json.groovy.* assert new JsonSlurper().parseText( new JsonGroovyBuilder().json {     book(title: "Groovy in Action",          author: "Dierk König et al") }.toString ()).book.title == "Groovy in Action" 24 jeudi 21 octobre 2010
  • 28. Grape improvements (2/4) • Shorter module / artifact / version parameter – Example of an annotation on a variable declaration @Grab('net.sf.json‐lib:json‐lib:2.3:jdk15') () def builder = new net.sf.json.groovy.JsonGroovyBuilder def books = builder.books {     book(title: "Groovy in Action", author: "Dierk Koenig") } assert books.toString() ==     '{"books":{"book":{"title":"Groovy in Action",' +      '"author":"Dierk Koenig"}}}' 25 jeudi 21 octobre 2010
  • 29. Grape improvements (3/4) • Groovy 1.7 introduced Grab resolver – For when you need to specify a specific repository for a given dependency @GrabResolver(     name = 'restlet.org',     root = 'http://maven.restlet.org') @Grab('org.restlet:org.restlet:1.1.6') import org.restlet.Restlet 26 jeudi 21 octobre 2010
  • 30. Grape improvements (4/4) • Groovy 1.7.5 even further shrinks the grab resolver definition: @Gra bResolver('http://maven.restlet.org') @Grab('org.restlet:org.restlet:1.1.6') import org.restlet.Restlet 27 jeudi 21 octobre 2010
  • 31. Power Asserts (1/2) • Much better assert statement! – Invented and developed in the Spock framework • Given this script... def energy = 7200 * 10**15 + 1 def mass = 80 def celerity = 300000000 assert energy == mass * celerity ** 2 28 jeudi 21 octobre 2010
  • 32. Power Asserts (2/2) • You’ll get a more comprehensible output 29 jeudi 21 octobre 2010
  • 33. Easier AST Transformations • AST Transformations are a very powerful feature • But are still rather hard to develop – Need to know the AST API closely • To help with authoring your own transformations, we’ve introduced – the AST Viewer in the Groovy Console – the AST Builder 30 jeudi 21 octobre 2010
  • 34. AST Viewer 31 jeudi 21 octobre 2010
  • 35. AST Builder // Ability to build AST parts // ‐‐> from a String new AstBui lder().buildFromString(''' "Hello" ''') // ‐‐> from code new AstBuilder().buildFromCode { "Hello" } // ‐‐> from a specification  { List<ASTNo de> nodes = new AstBuilder().buildFromSpec     block {         returnStatement {             constant "Hello"         }     } } 32 jeudi 21 octobre 2010
  • 36. Customize the Groovy Truth! • Ability to customize the truth by implementing a boolean asBoolean() method class Predicate {     boolean value     boolean asBoolean() { value } } def tr uePred  = new Predicate(value: true) def fals ePred = new Predicate(value: false) assert truePred && !falsePred 33 jeudi 21 octobre 2010
  • 37. SQL support refinements // batch statements sql.withBatch { stmt ‐> e ‐> ["Paul", "Jochen", "Guillaume"].each { nam e)"  stmt.addBat ch "insert into PERSON (name) values ($nam } } // transaction support def persons = sql.dataSet("person") sql.withTransaction {   persons.add name: "Paul"   persons.add name: "Jochen"   persons.add name: "Guillaume"   persons.add name: "Roshan" } 34 jeudi 21 octobre 2010
  • 38. Groovy 1.7.x changes • Since Groovy 1.7.0, Groovy 1.7.1, 1.7.2, 1.7.3, 1.7.4 and 1.7.5 have been released already! • Here’s what’s new! 35 jeudi 21 octobre 2010
  • 39. Map improvements // map auto‐vification def m = [:].withDefault { key ‐> "Default" } assert m['z'] == "Default"  assert m['a'] == "Default" // default sort m.sort() // sort with a comparator m.sort({ a, b ‐> a <=> b } as Comparator) 36 jeudi 21 octobre 2010
  • 40. XML back to String • Ability to retrieve the XML string from a node from an XmlSlurper GPathResult def xml = """ <books>      <book isbn="12345">Groovy in Action</book> </books> """ def root = new XmlSlurper().parseText(xml) def someNode = root.book def bu ilder = new StreamingMarkupBuilder() assert build er.bindNode(someNode).toString() ==         "<book  isbn='12345'>Groovy in Action</book>" 37 jeudi 21 octobre 2010
  • 41. Currying improvements // right currying def divide = { a, b ‐> a / b } def halver = divide.rcurry(2) assert halver(8) == 4   // currying n‐th parameter def jo inWithSeparator = { one, sep, two ‐>     one + sep + two } def joinWithComma =      jo inWithSeparator.ncurry(1, ', ') assert joinWithComma('a', 'b') == 'a, b' 38 jeudi 21 octobre 2010
  • 42. New String methods println """ println """     def method() {     |def method() {         return 'bar'     |    return 'bar'     }     |} """.stripIndent() """.stripMargin('|') // string "translation" (UNIX tr) assert 'hello'.tr('z‐a', 'Z‐A') == 'HELLO'  WAAAA!' asse rt 'Hello World!'.tr('a‐z', 'A') == 'HAAAA 2d!' assert 'Hell o World!'.tr('lloo', '1234') == 'He224 W4r // capitalize the first letter assert 'h'.capitalize() == 'H' assert 'hello'.capitalize() == 'Hello' rld' asse rt 'hello world'.capitalize() == 'Hello wo mmand) // tab/space (un)expansion (UNIX expand co 7 8        ' assert '1234567t8t '.expand() == '123456 ' assert '    x    '.unexpand() == '    xt  39 jeudi 21 octobre 2010
  • 43. ...and beyond! jeudi 21 octobre 2010
  • 44. Groovy 1.8 & beyond • Still subject to discussion • Always evolving roadmap • Things may change! 41 jeudi 21 octobre 2010
  • 45. What’s cooking? jeudi 21 octobre 2010
  • 46. What we’re working on • More runtime performance improvements • Closures – closure annotation parameters – closure composition – closure memoization • New AST transformations • Gradle build • Modularizing Groovy • Align with JDK 7 / Java 7 / Project Coin • Enhanced DSL support • AST Templates 43 jeudi 21 octobre 2010
  • 47. Closure annotation parameters • Groovy 1.5 brought Java 5 annotations • What if... we could go beyond what Java offered? – In 1.7, we can put annotations on packages, imports and variable declarations – But annotations are still limited in terms of parameters they allow • Here comes closure annotation parameters! – Groovy 1.8 will give us the ability to access annotation with closure parameters at runtime 44 jeudi 21 octobre 2010
  • 48. GContracts • Closures are already allowed in the Groovy 1.7 Antlr grammar – André Steingreß created GContracts, a «design by contract» module // a class invariant @I nvariant({ name.size() > 0 && age > ageLimit() })   // a method pre‐condition @Requires({ message != null })   // a method post‐condition @Ensures({ returnResult % 2 == 0 }) 45 jeudi 21 octobre 2010
  • 49. Closure composition • Functional flavor! def plus2  = { it + 2 } def times3 = { it * 3 }   def composed1 = plus2 << times3 assert composed1(3) == 11 assert composed1(4) == plus2(times3(4))   def composed2 = times3 << plus2 assert composed2(3) == 15 assert composed2(5) == times3(plus2(5))   // reverse composition assert composed1(3) == (times3 >> plus2)(3) 46 jeudi 21 octobre 2010
  • 50. Closure memoization • Memoization: remember the outcome of previous (ideally side-effect free) invocations def c = { a, b ‐> sleep 1000; a + b }.memoize() assert c(1, 2) == 3 // after 1000ms assert c(1, 2) == 3 // return immediately   // other forms: // at least 10 invocations cached def cAtLeast = { ... }.memoizeAtLeast(10) // at most 10 invocations cached def cAtMost = { ... }.memoizeAtMost(10) // between 10 and 20 invocations cached def cAtLeast = { ... }.memoizeBetween(10, 20) 47 jeudi 21 octobre 2010
  • 51. New AST Transformations • Many new transformations coming up for removing even more boiler plate code – @Log, inject a logger in your classes – @Field, creates a field in your scripts – @PackageScope improvements (methods & fields) – @Synchronized, providing safer synchronization semantics – @InheritConstructor, ex. when extending Exception – @IndexedProperties, JavaBeans indexed property support – @AutoClone, automatic cloning of your beans – @AutoExternalizable, automatic externalization of your beans – @Canonical, adding equals, hashCode, toString – @EqualsAndHashCode, only adding equals and hashCode – @ToString, only adding toString – @TupleConstructor, for adding a tuple constructor 48 jeudi 21 octobre 2010
  • 52. jeudi 21 octobre 2010
  • 53. jeudi 21 octobre 2010
  • 54. bu ild dh oc oo vy ore a lar Gr M du s! o e m rom H an Mor ef M or jeudi 21 octobre 2010
  • 55. More modular build • «Not everybody needs everything!» ™ • A lighter Groovy-core – what’s in groovy-all? • Modules – test, jmx, swing, xml, sql, web, template – integration (bsf, jsr-223) – tools (groovydoc, groovyc, shell, console, java2groovy) 50 jeudi 21 octobre 2010
  • 56. Java 7 / 8 / Project Coin • JSR-292 InvokeDynamic • Simple Closures (8) • Proposals from Project Coin – Strings in switch (7) – Automatic Resource Management (7) – Improved generics type inference (diamond <>) (7) – Simplified varargs method invocation (7) – Better integral literals (7) – Language support for collections (8?) 51 jeudi 21 octobre 2010
  • 57. Java 7 / 8 / Project Coin • JSR-292 InvokeDynamic • Simple Closures (8) • Proposals from Project Coin – Strings in switch (7) – Automatic Resource Management (7) – Improved generics type inference (diamond <>) (7) – Simplified varargs method invocation (7) – Better integral literals (7) – Language support for collections (8?) 51 jeudi 21 octobre 2010
  • 58. Java 7 / 8 / Project Coin • JSR-292 InvokeDynamic • Simple Closures (8) • Proposals from Project Coin – Strings in switch (7) – Automatic Resource Management (7) – Improved generics type inference (diamond <>) (7) – Simplified varargs method invocation (7) – Better integral literals (7) – Language support for collections (8?) 51 jeudi 21 octobre 2010
  • 59. Java 7 / 8 / Project Coin • JSR-292 InvokeDynamic • Simple Closures (8) • Proposals from Project Coin – Strings in switch (7) – Automatic Resource Management (7) – Improved generics type inference (diamond <>) (7) – Simplified varargs method invocation (7) – Better integral literals (7) – Language support for collections (8?) 51 jeudi 21 octobre 2010
  • 60. Java 7 / 8 / Project Coin • JSR-292 InvokeDynamic • Simple Closures (8) • Proposals from Project Coin – Strings in switch (7) – Automatic Resource Management (7) – Improved generics type inference (diamond <>) (7) – Simplified varargs method invocation (7) – Better integral literals (7) – Language support for collections (8?) 51 jeudi 21 octobre 2010
  • 61. Improved DSL support • GEP-3: an extended command expression DSL – Groovy Extension Proposal #3 • Command expressions – basically top-level statements without parens – combine named and non-named arguments in the mix • for nicer Domain-Specific Languages – (methodName arguments )* 52 jeudi 21 octobre 2010
  • 62. Before GEP-3 • The idea: extend command-expressions, beyond top-level statements, for chained method calls • Before send("Hello").to("Graeme") check(that: margherita).tastes(good) sell(100.shares).of(MSFT) take(2.pills).of(chloroquinine).after(6.hours) wait(10.minutes).and(execute {  }) blend(red, green).of(acrylic) 53 jeudi 21 octobre 2010
  • 63. With GEP-3 • The idea: extend command-expressions, beyond top-level statements, for chained method calls • After send "Hello"  to "Graeme" check that: margherita  tastes good sell 100.shares  of MSFT take 2.pills  of chloroquinine  after 6.hours wait 10.minutes  and execute {  } blend red, green  of acrylic 54 jeudi 21 octobre 2010
  • 64. With GEP-3 • The idea: extend command-expressions, beyond top-level statements, for chained method calls • After Less & co pare send "Hello"  to "Graeme" check that: margherita  tastes good mm ns sell 100.shares  of MSFT as take 2.pills  of chloroquinine  after 6.hours wait 10.minutes  and execute {  } blend red, green  of acrylic 54 jeudi 21 octobre 2010
  • 65. Summary SpringOne 2GX 2010. All rights reserved. Do not distribute without permission. jeudi 21 octobre 2010
  • 66. Summary (1/2) • No need to wait for Java 7, 8, 9... – closures, properties, interpolated strings, extended annotations, metaprogramming, [YOU NAME IT]... 56 jeudi 21 octobre 2010
  • 67. Summary (1/2) • No need to wait for Java 7, 8, 9... – closures, properties, interpolated strings, extended annotations, metaprogramming, [YOU NAME IT]... ’s s till Gro ovy no vat ive in 20 03! si nce 56 jeudi 21 octobre 2010
  • 68. Summary (2/2) • But it’s more than just a language, it’s a very rich and active ecosystem! – Grails, Griffon, Gradle, GPars, Spock, Gaelyk... 57 jeudi 21 octobre 2010
  • 69. Q&A SpringOne 2GX 2010. All rights reserved. Do not distribute without permission. jeudi 21 octobre 2010
  • 70. Thanks for your attention! e e Laforg velopment Gu illaum oovy De m of Gr e@gmail.co Head laforg E mail: g glaforge @ T witter: • References: • http://gaelyk.appspot.com/ • http://groovy.codehaus.org/ • http://code.google.com/appengine/ 59 jeudi 21 octobre 2010
  • 71. Images used in this presentation House / past: http://www.flickr.com/photos/jasonepowell/3680030831/sizes/o/ Present clock: http://www.flickr.com/photos/38629278@N04/3784344944/sizes/o/ Future: http://www.flickr.com/photos/befuddledsenses/2904000882/sizes/l/ Cooking: http://www.flickr.com/photos/eole/449958332/sizes/l/ Puzzle: http://www.everystockphoto.com/photo.php?imageId=263521 Light bulb: https://newsline.llnl.gov/retooling/mar/03.28.08_images/lightBulb.png Speed limit : http://www.morguefile.com/archive/display/18492 Warehouse : http://www.morguefile.com/archive/display/85628 Check mark: http://www.lnl.infn.it/~epics/WikiDumps/localhost/600px-symbol_ok.svg.png 60 jeudi 21 octobre 2010