際際滷

際際滷Share a Scribd company logo
GROOVY E DSL
BY TIZIANO LATTISI
INDICE
 cos竪 Groovy?
 caratteristiche interessanti (a mio giudizio), in ordine
arbitrariamente sparso
 cos竪 un DSL?
 caratteristiche che rendono Groovy adatto a costruire un DSL
 un esempio semplice (lo facciamo al volo)
 un esempio meno semplice (non lo facciamo al volo)
nota: in parallelo vedremo esempi
COS GROOVY (PARTE 1)?
 linguaggio per la JVM alternativo a Java
 ispirato a: Ruby, Python, Smalltalk
 consente compilazione dinamica, ma pu嘆 anche
generare bytecode
 tipizzazione forte dinamica
 closure
COMMAND-LINE GROOVY
HELLO GROOVY
 $ groovy -e println Hello Groovy!
 $ echo println Hello Groovy > hello.groovy
$ groovy hello.groovy!
 $ groovy -Dmsg=Groovy -e println Hello  +
System.getProperty(msg)
COMMAND-LINE GROOVY
SWITCH -N -P -I
 $ printf 1n2 > data.txt
$ groovy -n -e println line.toLong()*2 data.txt
2
4!
 $ groovy -i.bak n -p -e line.toLong()*2 data.txt
$ cat data.txt
2
4
$ cat data.txt.bak
1
2
COMMAND-LINE GROOVY
SWITCH -L
 $ groovy -l 1234 -e if(line==DATE){println new Date()}
Groovy is listening on port 1234

$ telnet localhost 1234
Connect to localhost.
Escape character is ^].
DATE
Mon Mar 17 21:38:49 CET 2014!
 $ groovy -l 80 SimpleWebServer.groovy

Esempio nei sorgenti Groovy: serve i file di una cartella
come webserver
COS GROOVY (PARTE 2)?
 竪 possibile usare direttamente lAPI Java
 accetta (salvo alcune eccezioni) anche sintassi Java (es. {1,2,3,4} non 竪
array, ma [1,2,3,4] 竪 un ArrayList)
 import automatico (di convenienza) di alcune classi Java (es. java.io,
java.lang, java.net, java.util)
 println -> System.out.println
 parentesi opzionali nella chiamata a metodi
 notazione breve per getter e setter (o.鍖eld -> o.getField())
 ; opzionale (salvo alcune eccezioni)
 return opzionale (viene restituita lultima valutazione)
 this usata in contesti statici punta alla classe
COS GROOVY (PARTE 3)?
 GString interpolation: Hello ${name}
 Lazily interpolation (eval in conversione a String): Nr. ${-> i}
 == -> equals, equals -> is: non pi湛 a != null && a.equals() !!
 in: 竪 un operatore basato su contains(): 3 in [1,2,3,4]
 sintassi nativa per alcune strutture dati: [1,2,3] list, [TN:Trento,
BZ:Bolzano] map, 1..10 range
 contesti booleani: if( myString!=null && myString.length>0 ){} ->
if(myString){}
 safe-dereferencing: email?.destinatario?.indirizzo
 costrutto and-or (Elvis operator):
def result = name != null ? name : Unknow
FOR E FOR EACH
 for (int i=0; i<n; i++) {  }!
 for (i in 0..n-1) {  }!
 for (i in 0..<n) {  }!
 n.times {  }
 (1..5).each { println nr. $it }!
 1..5 instanceof List!
 { println nr. $it }(3)
nr. 3
GROOVY BEANS
class Book {
String title
String description
}

def b1 = new Book()
b1.setTitle(Anna Karenina)
b1.description = A very long book!
println b2.getDescription()
println b2.title

def b2 = new Book(title:Anna Karenina)
println b2.title
ALTRO SUI GROOVY BEANS
 Annotation based AST transformation (groovy.transform.*):!
 @Immutable (read only bean)!
 @ToString(includeNames=true, excludes=description,year)!
 @EqualsAndHashCode!
 @Canonical (@ToString + @EqualsAndHashCode)!
 @TupleConstructor -> new Book(Anna Karenina, Very long
book)!
 @AutoClone(style=AutoCloneStyle.COPY_CONSTRUCTOR)

def book1 = new Book(title:Anna Karenina)
def book2 = book1.clone()
assert book1.title == book2.title!
 AutoCloneStyle.SERIALIZABLE se implementa Serializable
ALTRE COSE BELLE
 methodMissing e propertyMissing per gestire
accessi a propriet o metodi mancanti
 supporto nativo per markup XML, Json (Slurper e
Builder)
 conversioni bean in xml e json
 ExpandoMetaClass
 built-in memoize
DSL
DOMAIN SPECIFIC LANGUAGE
 Linguaggio di programmazione dedicato ad uno
speci鍖co dominio (contrapposto a general-purpose)
 statistica (R e S)
 programmazione matriciale (Mata)
 Logo
 SQL
DEFINIRE UN DSL IN GROOVY
Combinazione di tre punti chiave:
 鍖uent API
 embedded shell
 speci鍖cit del linguaggio
FLUENT API
 un implementazione di un API method chaining,
ovvero che permette chiamate di metodi a catena.
Es. JavaFX
Scene scene = SceneBuilder.create().width(516).height(387)
! .root(
! ! GroupBuilder.create().children(
! ! ! ImageViewBuilder.create().image(new Image(..)),
! ! ! [omissam]
! ! ).build()).build();
EMBEDING GROOVY IN JAVA
// Semplice esecuzione di codice Groovy!
GroovyShell shell = new GroovyShell();
String groovyCode = println Hello  + Groovy;
String out = shell.evaluate(groovyCode);
// Esecuzione codice Groovy con variabile embeddata!
Book myBook = new Book();
myBook.setTitle(Anna Karenina);!
Binding binding = new Binding();
binding.setVariable(book, myBook);
String groovyCode = println Reading  + book.title;
GroovyShell shell = new GroovyShell(binding);
String out = shell.evaluate(groovyCode);
SPECIFICIT DI GROOVY
 le chiamate di metodi possono omettere le parentesi
 scriptBaseClass: la classe script base che rappresenta il contesto
di esecuzione dello script
 ImportCustomizer: importazione diretta nello script di classi e
package (anche *)
 SecureASTCustomizer: gestione della sicurezza (es. liste
bianche/nere)
 ASTTransformationCustomizer: per aggiungere
automaticamente annotazioni di trasformazione ai metodi
ESEMPIO SEMPLICE
Voglio creare un DSL in grado di eseguire:
compute 4 plus 3 plus 2 minus 1 print total!
 Una classe che implementa i metodi di linguaggio (compute, plus, minus, etc) come API
鍖uent
 Una classe astratta come base dello script groovy (si occuper di proxare i metodi sullo
script)
 Un enum per le costanti (es. total)
 GroovyShell con:
 binding della classe linguaggio
 classe base astratta (vedi sopra)
 importazione custom delle costanti (vedi sopra)
Vediamo in pratica come procedere! (sorry, no slides here)
LA CLASSE DI LINGUAGGIO
class Language {
Integer tot;
def compute(Integer a){
tot=a
this
}
def plus(Integer a){
tot += a
this
}
def minus(Integer a){
tot -= a
this
}
def print(Consts c){
tot
}
}
LA SCRIPTBASE E LA COSTANTE
abstract class AbstractScriptBaseClass extends Script{
def compute(Integer a){
this.lang.compute(a)
}
def plus(Integer a){
this.lang.plus(a)
}
def minus(Integer a){
this.lang.minus(a)
}
def print(String t){
this.lang.print(t)
}
}
public enum Consts {
total
}
TESTIAMO LAPI
void testAPI() {

Language lang = new Language()
String total = "total"

// test API con sintassi tradizionale
Integer tot1 = lang.compute(4).plus(3).plus(2).minus(1).print(total)

// test API omettendo le parentesi
Integer tot2 = lang.compute 4 plus 3 plus 2 minus 1 print total

assert tot1 == 8
assert tot2 == 8

}
TESTIAMO IL DSL
void testShell() {

// il codice scritto nel DSL
def code = "compute 4 plus 3 plus 2 minus 1 print total"

Language lang = new Language()
Binding binding = new Binding();
binding.setVariable("lang", lang)

CompilerConfiguration conf = new CompilerConfiguration()
conf.scriptBaseClass = AbstractScriptBaseClass.class.name

ImportCustomizer imports = new ImportCustomizer()
imports.addStaticStars(Consts.name)
conf.addCompilationCustomizers(imports)

GroovyShell shell = new GroovyShell(binding, conf)
Integer tot = (Integer) shell.evaluate(code)

assert tot == 8
}
ESEMPIO MENO SEMPLICE
Un DSL per de鍖nire e risolvere problemi di geometria piana euclidea
(https://github.com/tizianolattisi/peg)
create triangle name "ABC"
extend "AC" to "D" with measure:"BC"
extend "BC" to "E" with measure:"AC"
create segment name "ED"
extend "DE" to "H"
extend "AB" to "H"
apply "10.8" on "ad", "bc" //angoli opposti
apply "10.3" on "CED", "ABC"
apply "10.6" on "ABC", "cba", "CED", "edc"
create segment name "BD"
apply "10.10" on "BCD", "BC", "CD"
Tiziano Lattisi
Grazie a 岳顎岳岳庄!.

More Related Content

Viewers also liked (20)

Pensiero Orientato Agli Oggetti
Pensiero Orientato Agli OggettiPensiero Orientato Agli Oggetti
Pensiero Orientato Agli Oggetti
Silvano Natalizi - ITIS ALESSANDRO VOLTA PERUGIA
Java
JavaJava
Java
Antonio Furone
Java 01
Java 01Java 01
Java 01
davide ficano
(E book pdf) thinking in patterns with java
(E book   pdf) thinking in patterns with java(E book   pdf) thinking in patterns with java
(E book pdf) thinking in patterns with java
Raffaella D'angelo
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳 亳 仂舒仆亳 舒亟仂从"
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳  亳 仂舒仆亳 舒亟仂从"丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳  亳 仂舒仆亳 舒亟仂从"
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳 亳 仂舒仆亳 舒亟仂从"
Expolink
Linguaggio di programmazione java - Scheda corso LEN
Linguaggio di programmazione java - Scheda corso LENLinguaggio di programmazione java - Scheda corso LEN
Linguaggio di programmazione java - Scheda corso LEN
LEN Learning Education Network
(Ebook pdf) java programming language basics
(Ebook pdf)   java programming language basics(Ebook pdf)   java programming language basics
(Ebook pdf) java programming language basics
Raffaella D'angelo
Informatica di base
Informatica di baseInformatica di base
Informatica di base
Bruno Montalto
OOP Java
OOP JavaOOP Java
OOP Java
Saif Kassim
Java Programming Language
Java Programming LanguageJava Programming Language
Java Programming Language
Pasquale Paola
Java e il paradigma a oggetti v2
Java e il paradigma a oggetti v2Java e il paradigma a oggetti v2
Java e il paradigma a oggetti v2
cinziabb
Java e il paradigma a oggetti
Java e il paradigma a oggettiJava e il paradigma a oggetti
Java e il paradigma a oggetti
cinziabb
Corso Programmazione Java Base
Corso Programmazione Java BaseCorso Programmazione Java Base
Corso Programmazione Java Base
K-Tech Formazione
Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Programmazione a oggetti tramite la macchina del caff辿 (1/3)Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Marcello Missiroli
Python nel primo biennio della scuola superiore
Python nel primo biennio della scuola superiorePython nel primo biennio della scuola superiore
Python nel primo biennio della scuola superiore
guestc11532
Programmazione ad oggetti
Programmazione ad oggettiProgrammazione ad oggetti
Programmazione ad oggetti
Anna_1969
Sviluppare applicazioni mobile native in html e java script
Sviluppare applicazioni mobile native in html e java scriptSviluppare applicazioni mobile native in html e java script
Sviluppare applicazioni mobile native in html e java script
Fabio Franzini
Programmazione ad oggetti
Programmazione ad oggettiProgrammazione ad oggetti
Programmazione ad oggetti
mariacaporale
Tesina Maturit 2012-2013
Tesina Maturit 2012-2013 Tesina Maturit 2012-2013
Tesina Maturit 2012-2013
Michele Loda
(E book ita) java introduzione alla programmazione orientata ad oggetti in ...
(E book ita) java   introduzione alla programmazione orientata ad oggetti in ...(E book ita) java   introduzione alla programmazione orientata ad oggetti in ...
(E book ita) java introduzione alla programmazione orientata ad oggetti in ...
Raffaella D'angelo
(E book pdf) thinking in patterns with java
(E book   pdf) thinking in patterns with java(E book   pdf) thinking in patterns with java
(E book pdf) thinking in patterns with java
Raffaella D'angelo
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳 亳 仂舒仆亳 舒亟仂从"
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳  亳 仂舒仆亳 舒亟仂从"丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳  亳 仂舒仆亳 舒亟仂从"
丐. 仍舒亟亳仄亳 于舒仆仂于. "舒从 仗仂仄仂 亳仆亳 亳 仂舒仆亳 舒亟仂从"
Expolink
Linguaggio di programmazione java - Scheda corso LEN
Linguaggio di programmazione java - Scheda corso LENLinguaggio di programmazione java - Scheda corso LEN
Linguaggio di programmazione java - Scheda corso LEN
LEN Learning Education Network
(Ebook pdf) java programming language basics
(Ebook pdf)   java programming language basics(Ebook pdf)   java programming language basics
(Ebook pdf) java programming language basics
Raffaella D'angelo
Informatica di base
Informatica di baseInformatica di base
Informatica di base
Bruno Montalto
Java Programming Language
Java Programming LanguageJava Programming Language
Java Programming Language
Pasquale Paola
Java e il paradigma a oggetti v2
Java e il paradigma a oggetti v2Java e il paradigma a oggetti v2
Java e il paradigma a oggetti v2
cinziabb
Java e il paradigma a oggetti
Java e il paradigma a oggettiJava e il paradigma a oggetti
Java e il paradigma a oggetti
cinziabb
Corso Programmazione Java Base
Corso Programmazione Java BaseCorso Programmazione Java Base
Corso Programmazione Java Base
K-Tech Formazione
Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Programmazione a oggetti tramite la macchina del caff辿 (1/3)Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Programmazione a oggetti tramite la macchina del caff辿 (1/3)
Marcello Missiroli
Python nel primo biennio della scuola superiore
Python nel primo biennio della scuola superiorePython nel primo biennio della scuola superiore
Python nel primo biennio della scuola superiore
guestc11532
Programmazione ad oggetti
Programmazione ad oggettiProgrammazione ad oggetti
Programmazione ad oggetti
Anna_1969
Sviluppare applicazioni mobile native in html e java script
Sviluppare applicazioni mobile native in html e java scriptSviluppare applicazioni mobile native in html e java script
Sviluppare applicazioni mobile native in html e java script
Fabio Franzini
Programmazione ad oggetti
Programmazione ad oggettiProgrammazione ad oggetti
Programmazione ad oggetti
mariacaporale
Tesina Maturit 2012-2013
Tesina Maturit 2012-2013 Tesina Maturit 2012-2013
Tesina Maturit 2012-2013
Michele Loda
(E book ita) java introduzione alla programmazione orientata ad oggetti in ...
(E book ita) java   introduzione alla programmazione orientata ad oggetti in ...(E book ita) java   introduzione alla programmazione orientata ad oggetti in ...
(E book ita) java introduzione alla programmazione orientata ad oggetti in ...
Raffaella D'angelo

Similar to Groovy e Domain Specific Languages (20)

Introduzione a TypeScript
Introduzione a TypeScriptIntroduzione a TypeScript
Introduzione a TypeScript
Sinergia Totale
Sviluppo web dall'antichit all'avanguardia e ritorno
Sviluppo web  dall'antichit all'avanguardia e ritornoSviluppo web  dall'antichit all'avanguardia e ritorno
Sviluppo web dall'antichit all'avanguardia e ritorno
lordarthas
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore RomeoHTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
marcocasario
Codemotion 2012 creare un proprio linguaggio di programmazione
Codemotion 2012 creare un proprio linguaggio di programmazioneCodemotion 2012 creare un proprio linguaggio di programmazione
Codemotion 2012 creare un proprio linguaggio di programmazione
Gabriele Guizzardi
Vb.Net
Vb.NetVb.Net
Vb.Net
Maurizio Farina
LINQ, Entities Framework & ORMs
LINQ, Entities Framework & ORMsLINQ, Entities Framework & ORMs
LINQ, Entities Framework & ORMs
JUG Genova
Pycrashcourse
PycrashcoursePycrashcourse
Pycrashcourse
rik0
Mini Corso Java - Parte 1
Mini Corso Java - Parte 1Mini Corso Java - Parte 1
Mini Corso Java - Parte 1
Ezio Sperduto, PhD
DotNetToscana - Sessione TypeScript
DotNetToscana - Sessione TypeScriptDotNetToscana - Sessione TypeScript
DotNetToscana - Sessione TypeScript
Sinergia Totale
Web base-03-js-numeri stringearray
Web base-03-js-numeri stringearrayWeb base-03-js-numeri stringearray
Web base-03-js-numeri stringearray
Studiabo
JOSM per ninja
JOSM per ninjaJOSM per ninja
JOSM per ninja
Andrea Musuruane
Linux@Unina
Linux@UninaLinux@Unina
Linux@Unina
NaLUG
Javascript avanzato: sfruttare al massimo il web
Javascript avanzato: sfruttare al massimo il webJavascript avanzato: sfruttare al massimo il web
Javascript avanzato: sfruttare al massimo il web
Roberto Messora
Al telefono con Adhearsion e Ruby
Al telefono con Adhearsion e RubyAl telefono con Adhearsion e Ruby
Al telefono con Adhearsion e Ruby
Luca Pradovera
REST con Jersey
REST con JerseyREST con Jersey
REST con Jersey
Fabio Bonfante
Web base - Javascript (Node.js): Elementi di base
Web base - Javascript (Node.js): Elementi di baseWeb base - Javascript (Node.js): Elementi di base
Web base - Javascript (Node.js): Elementi di base
Annalisa Vignoli
Functional Programming in Java - Le Espressioni Lambda
Functional Programming in Java - Le Espressioni LambdaFunctional Programming in Java - Le Espressioni Lambda
Functional Programming in Java - Le Espressioni Lambda
Ezio Sperduto, PhD
Acadevmy - TypeScript Overview
Acadevmy - TypeScript OverviewAcadevmy - TypeScript Overview
Acadevmy - TypeScript Overview
Francesco Sciuti
Jug 30 10 04 Jdo
Jug 30 10 04 JdoJug 30 10 04 Jdo
Jug 30 10 04 Jdo
Massimiliano Dess狸
Introduzione a TypeScript
Introduzione a TypeScriptIntroduzione a TypeScript
Introduzione a TypeScript
Sinergia Totale
Sviluppo web dall'antichit all'avanguardia e ritorno
Sviluppo web  dall'antichit all'avanguardia e ritornoSviluppo web  dall'antichit all'avanguardia e ritorno
Sviluppo web dall'antichit all'avanguardia e ritorno
lordarthas
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore RomeoHTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
HTML5 Italy: Mai pi湛 CSS, fogli di stile moderni con LESS - Salvatore Romeo
marcocasario
Codemotion 2012 creare un proprio linguaggio di programmazione
Codemotion 2012 creare un proprio linguaggio di programmazioneCodemotion 2012 creare un proprio linguaggio di programmazione
Codemotion 2012 creare un proprio linguaggio di programmazione
Gabriele Guizzardi
LINQ, Entities Framework & ORMs
LINQ, Entities Framework & ORMsLINQ, Entities Framework & ORMs
LINQ, Entities Framework & ORMs
JUG Genova
Pycrashcourse
PycrashcoursePycrashcourse
Pycrashcourse
rik0
DotNetToscana - Sessione TypeScript
DotNetToscana - Sessione TypeScriptDotNetToscana - Sessione TypeScript
DotNetToscana - Sessione TypeScript
Sinergia Totale
Web base-03-js-numeri stringearray
Web base-03-js-numeri stringearrayWeb base-03-js-numeri stringearray
Web base-03-js-numeri stringearray
Studiabo
Linux@Unina
Linux@UninaLinux@Unina
Linux@Unina
NaLUG
Javascript avanzato: sfruttare al massimo il web
Javascript avanzato: sfruttare al massimo il webJavascript avanzato: sfruttare al massimo il web
Javascript avanzato: sfruttare al massimo il web
Roberto Messora
Al telefono con Adhearsion e Ruby
Al telefono con Adhearsion e RubyAl telefono con Adhearsion e Ruby
Al telefono con Adhearsion e Ruby
Luca Pradovera
Web base - Javascript (Node.js): Elementi di base
Web base - Javascript (Node.js): Elementi di baseWeb base - Javascript (Node.js): Elementi di base
Web base - Javascript (Node.js): Elementi di base
Annalisa Vignoli
Functional Programming in Java - Le Espressioni Lambda
Functional Programming in Java - Le Espressioni LambdaFunctional Programming in Java - Le Espressioni Lambda
Functional Programming in Java - Le Espressioni Lambda
Ezio Sperduto, PhD
Acadevmy - TypeScript Overview
Acadevmy - TypeScript OverviewAcadevmy - TypeScript Overview
Acadevmy - TypeScript Overview
Francesco Sciuti

More from Tiziano Lattisi (6)

JugTAAS ReSTful
JugTAAS ReSTfulJugTAAS ReSTful
JugTAAS ReSTful
Tiziano Lattisi
ZoeFX: un framework MVC per JavaFX
ZoeFX: un framework MVC per JavaFXZoeFX: un framework MVC per JavaFX
ZoeFX: un framework MVC per JavaFX
Tiziano Lattisi
JavaFX2: una panoramica
JavaFX2: una panoramicaJavaFX2: una panoramica
JavaFX2: una panoramica
Tiziano Lattisi
VCS - DVCS - GIT-FLOW
VCS - DVCS - GIT-FLOWVCS - DVCS - GIT-FLOW
VCS - DVCS - GIT-FLOW
Tiziano Lattisi
JPA2 - a brief intro
JPA2 - a brief introJPA2 - a brief intro
JPA2 - a brief intro
Tiziano Lattisi
PyPaPi Qt Java Framework
PyPaPi Qt Java FrameworkPyPaPi Qt Java Framework
PyPaPi Qt Java Framework
Tiziano Lattisi
ZoeFX: un framework MVC per JavaFX
ZoeFX: un framework MVC per JavaFXZoeFX: un framework MVC per JavaFX
ZoeFX: un framework MVC per JavaFX
Tiziano Lattisi
JavaFX2: una panoramica
JavaFX2: una panoramicaJavaFX2: una panoramica
JavaFX2: una panoramica
Tiziano Lattisi
VCS - DVCS - GIT-FLOW
VCS - DVCS - GIT-FLOWVCS - DVCS - GIT-FLOW
VCS - DVCS - GIT-FLOW
Tiziano Lattisi
PyPaPi Qt Java Framework
PyPaPi Qt Java FrameworkPyPaPi Qt Java Framework
PyPaPi Qt Java Framework
Tiziano Lattisi

Groovy e Domain Specific Languages

  • 1. GROOVY E DSL BY TIZIANO LATTISI
  • 2. INDICE cos竪 Groovy? caratteristiche interessanti (a mio giudizio), in ordine arbitrariamente sparso cos竪 un DSL? caratteristiche che rendono Groovy adatto a costruire un DSL un esempio semplice (lo facciamo al volo) un esempio meno semplice (non lo facciamo al volo) nota: in parallelo vedremo esempi
  • 3. COS GROOVY (PARTE 1)? linguaggio per la JVM alternativo a Java ispirato a: Ruby, Python, Smalltalk consente compilazione dinamica, ma pu嘆 anche generare bytecode tipizzazione forte dinamica closure
  • 4. COMMAND-LINE GROOVY HELLO GROOVY $ groovy -e println Hello Groovy! $ echo println Hello Groovy > hello.groovy $ groovy hello.groovy! $ groovy -Dmsg=Groovy -e println Hello + System.getProperty(msg)
  • 5. COMMAND-LINE GROOVY SWITCH -N -P -I $ printf 1n2 > data.txt $ groovy -n -e println line.toLong()*2 data.txt 2 4! $ groovy -i.bak n -p -e line.toLong()*2 data.txt $ cat data.txt 2 4 $ cat data.txt.bak 1 2
  • 6. COMMAND-LINE GROOVY SWITCH -L $ groovy -l 1234 -e if(line==DATE){println new Date()} Groovy is listening on port 1234 $ telnet localhost 1234 Connect to localhost. Escape character is ^]. DATE Mon Mar 17 21:38:49 CET 2014! $ groovy -l 80 SimpleWebServer.groovy Esempio nei sorgenti Groovy: serve i file di una cartella come webserver
  • 7. COS GROOVY (PARTE 2)? 竪 possibile usare direttamente lAPI Java accetta (salvo alcune eccezioni) anche sintassi Java (es. {1,2,3,4} non 竪 array, ma [1,2,3,4] 竪 un ArrayList) import automatico (di convenienza) di alcune classi Java (es. java.io, java.lang, java.net, java.util) println -> System.out.println parentesi opzionali nella chiamata a metodi notazione breve per getter e setter (o.鍖eld -> o.getField()) ; opzionale (salvo alcune eccezioni) return opzionale (viene restituita lultima valutazione) this usata in contesti statici punta alla classe
  • 8. COS GROOVY (PARTE 3)? GString interpolation: Hello ${name} Lazily interpolation (eval in conversione a String): Nr. ${-> i} == -> equals, equals -> is: non pi湛 a != null && a.equals() !! in: 竪 un operatore basato su contains(): 3 in [1,2,3,4] sintassi nativa per alcune strutture dati: [1,2,3] list, [TN:Trento, BZ:Bolzano] map, 1..10 range contesti booleani: if( myString!=null && myString.length>0 ){} -> if(myString){} safe-dereferencing: email?.destinatario?.indirizzo costrutto and-or (Elvis operator): def result = name != null ? name : Unknow
  • 9. FOR E FOR EACH for (int i=0; i<n; i++) { }! for (i in 0..n-1) { }! for (i in 0..<n) { }! n.times { } (1..5).each { println nr. $it }! 1..5 instanceof List! { println nr. $it }(3) nr. 3
  • 10. GROOVY BEANS class Book { String title String description } def b1 = new Book() b1.setTitle(Anna Karenina) b1.description = A very long book! println b2.getDescription() println b2.title def b2 = new Book(title:Anna Karenina) println b2.title
  • 11. ALTRO SUI GROOVY BEANS Annotation based AST transformation (groovy.transform.*):! @Immutable (read only bean)! @ToString(includeNames=true, excludes=description,year)! @EqualsAndHashCode! @Canonical (@ToString + @EqualsAndHashCode)! @TupleConstructor -> new Book(Anna Karenina, Very long book)! @AutoClone(style=AutoCloneStyle.COPY_CONSTRUCTOR) def book1 = new Book(title:Anna Karenina) def book2 = book1.clone() assert book1.title == book2.title! AutoCloneStyle.SERIALIZABLE se implementa Serializable
  • 12. ALTRE COSE BELLE methodMissing e propertyMissing per gestire accessi a propriet o metodi mancanti supporto nativo per markup XML, Json (Slurper e Builder) conversioni bean in xml e json ExpandoMetaClass built-in memoize
  • 13. DSL DOMAIN SPECIFIC LANGUAGE Linguaggio di programmazione dedicato ad uno speci鍖co dominio (contrapposto a general-purpose) statistica (R e S) programmazione matriciale (Mata) Logo SQL
  • 14. DEFINIRE UN DSL IN GROOVY Combinazione di tre punti chiave: 鍖uent API embedded shell speci鍖cit del linguaggio
  • 15. FLUENT API un implementazione di un API method chaining, ovvero che permette chiamate di metodi a catena. Es. JavaFX Scene scene = SceneBuilder.create().width(516).height(387) ! .root( ! ! GroupBuilder.create().children( ! ! ! ImageViewBuilder.create().image(new Image(..)), ! ! ! [omissam] ! ! ).build()).build();
  • 16. EMBEDING GROOVY IN JAVA // Semplice esecuzione di codice Groovy! GroovyShell shell = new GroovyShell(); String groovyCode = println Hello + Groovy; String out = shell.evaluate(groovyCode); // Esecuzione codice Groovy con variabile embeddata! Book myBook = new Book(); myBook.setTitle(Anna Karenina);! Binding binding = new Binding(); binding.setVariable(book, myBook); String groovyCode = println Reading + book.title; GroovyShell shell = new GroovyShell(binding); String out = shell.evaluate(groovyCode);
  • 17. SPECIFICIT DI GROOVY le chiamate di metodi possono omettere le parentesi scriptBaseClass: la classe script base che rappresenta il contesto di esecuzione dello script ImportCustomizer: importazione diretta nello script di classi e package (anche *) SecureASTCustomizer: gestione della sicurezza (es. liste bianche/nere) ASTTransformationCustomizer: per aggiungere automaticamente annotazioni di trasformazione ai metodi
  • 18. ESEMPIO SEMPLICE Voglio creare un DSL in grado di eseguire: compute 4 plus 3 plus 2 minus 1 print total! Una classe che implementa i metodi di linguaggio (compute, plus, minus, etc) come API 鍖uent Una classe astratta come base dello script groovy (si occuper di proxare i metodi sullo script) Un enum per le costanti (es. total) GroovyShell con: binding della classe linguaggio classe base astratta (vedi sopra) importazione custom delle costanti (vedi sopra) Vediamo in pratica come procedere! (sorry, no slides here)
  • 19. LA CLASSE DI LINGUAGGIO class Language { Integer tot; def compute(Integer a){ tot=a this } def plus(Integer a){ tot += a this } def minus(Integer a){ tot -= a this } def print(Consts c){ tot } }
  • 20. LA SCRIPTBASE E LA COSTANTE abstract class AbstractScriptBaseClass extends Script{ def compute(Integer a){ this.lang.compute(a) } def plus(Integer a){ this.lang.plus(a) } def minus(Integer a){ this.lang.minus(a) } def print(String t){ this.lang.print(t) } } public enum Consts { total }
  • 21. TESTIAMO LAPI void testAPI() { Language lang = new Language() String total = "total" // test API con sintassi tradizionale Integer tot1 = lang.compute(4).plus(3).plus(2).minus(1).print(total) // test API omettendo le parentesi Integer tot2 = lang.compute 4 plus 3 plus 2 minus 1 print total assert tot1 == 8 assert tot2 == 8 }
  • 22. TESTIAMO IL DSL void testShell() { // il codice scritto nel DSL def code = "compute 4 plus 3 plus 2 minus 1 print total" Language lang = new Language() Binding binding = new Binding(); binding.setVariable("lang", lang) CompilerConfiguration conf = new CompilerConfiguration() conf.scriptBaseClass = AbstractScriptBaseClass.class.name ImportCustomizer imports = new ImportCustomizer() imports.addStaticStars(Consts.name) conf.addCompilationCustomizers(imports) GroovyShell shell = new GroovyShell(binding, conf) Integer tot = (Integer) shell.evaluate(code) assert tot == 8 }
  • 23. ESEMPIO MENO SEMPLICE Un DSL per de鍖nire e risolvere problemi di geometria piana euclidea (https://github.com/tizianolattisi/peg) create triangle name "ABC" extend "AC" to "D" with measure:"BC" extend "BC" to "E" with measure:"AC" create segment name "ED" extend "DE" to "H" extend "AB" to "H" apply "10.8" on "ad", "bc" //angoli opposti apply "10.3" on "CED", "ABC" apply "10.6" on "ABC", "cba", "CED", "edc" create segment name "BD" apply "10.10" on "BCD", "BC", "CD"
  • 24. Tiziano Lattisi Grazie a 岳顎岳岳庄!.