3 de julio de 2009

Groovy... una mirada superficial

Para que entiendan Grails primero tienen que entender Groovy ya que Grails esta basado en groovy, en este articulo doy un ejemplo trivial pero importante dado a los nuevos conceptos que nos da este lenguaje dinámico.
Groovy es un lenguaje moderno de programación que se ejecuta en la plataforma Java (JVM). Que ofrece una muy buena integración con el código Java existente al tiempo que intr oduce nuevas características como closures y metaprogramming.

En palabras de Jorge Ferro Groovy es un lenguaje orientado a objetos que genera código ejecutable (byte code)
para la máquina virtual de Java. Toma “prestado” las ideas de otros lenguajes como Smalltalk, Ruby y Python y mantiene una sintaxis familiar a la de Java, cosa muy conveniente para los “Javeros”

Sin mas preambulos vallamos a un ejemplo clásico que supongo que ya lo habran visto, el "hola mundo", para este ejemplo se asume que ya tienes instalado Groovy, que simplemente se reduce a bajar el .zip, y crear tu variable de entorno. Lo pruebas poniendo en la linea de comando "groovy -version".  aqui hay un articulo sobre el tema

[sourcecode language='java']
public class HolaMundo{
public static void main(String[] args){
System.out.println("Hola Mundo");
}
}
[/sourcecode]

y ahora por supuesto, el mismo ejemplo pero en Groovy, que en su forma mas sencilla es esto:

Abres la shell de groovy (groovysh) y escribes:
[sourcecode language='java']
println "Hola Mundo"
[/sourcecode]

Para un programador que recien se inicia en el mundo de los lenguajes de programacion, esto le puede parecer muy sencillo de comprender, pero para un desarrollador experimentado hay algo más... inmediatamente despues de haber visto el codigo (Groovy) estoy seguro de que tienen muchas preguntas.

Por favor, ahora si vayamos al ejemplo anterior (HolaMundo.java). Pues en este ejemplo se consolida varios conceptos básicos de java, por ejemplo; todos sabemos que lo primero que debemos hacer en java es crear un archivo con el nombre de la clase, asi pues para el ejemplo seria: HolaMundo.java. Despues, este ejemplo no correria si es que no no se tiene el 'public static void main', el uso de los punto y comas al final de cada sentencia, y asi podemos seguir repasando otros conceptos, y que despues de todas esas enseñanzas vengan de buenas a primeras y que me digan.... println "Hola Mundo"... pues lógico que tengo que levantar la mano y decir "que paso con lo anterior".

Esto es groovy, muchos ya lo conocen y con este ejemplo trivial he querido demostrar lo que Groovy puede hacer por nosotros (los programadores), disminuye drámaticamente las lineas de codigo a escribir, tiene la ventaja de los lenguajes dinamicos, y ademas conserva una sintaxis parecida a la que estamos acostumbrados en java.

Groovy es Java y Java es Groovy y no lo estoy diciendo en forma figurada, Para demostrarlo que mejor que un ejemplo:

Tenemos una clase Alumno.java
[sourcecode language='java']
public class Alumno{
private String nombre;
private Integer codigo;

public String getNombre(){
return nombre;
}
public void setNombre(String nombre){
this.nombre= nombre;
}
public Integer getCodigo(){
return codigo;
}
public void setCodigo(Integer codigo){
this.codigo=codigo;
}
}

[/sourcecode]
y ahora lo vamos hacer en Groovy

[sourcecode language='java']
class AlumnoGroovy{
String nombre
Integer codigo
}
[/sourcecode]

Hay que remarcar que en Groovy todas las clases son publicas (a menos que se especifique lo contrario) y todas las propiedades de la clases son privadas, y los metodos de las propiedades son publicos y el compilador groovy proporciona el conjunto de getter y setter de forma automatica.
Compilamos nuestros archivos

[sourcecode language='java']
$javac Alumno.java
// y en el caso de groovy
$groovyc AlumnoGroovy.groovy.
[/sourcecode]

Veremos los resultados utilizando el comando javap que se encargara de desensamblar un fichero class.

$javap -p Alumno

[sourcecode language='java']
Compiled from "Alumno.java"
public class Alumno extends java.lang.Object{
private java.lang.String nombre;
private java.lang.Integer codigo;
public Alumno();
public java.lang.String getNombre();
public void setNombre(java.lang.String);
public java.lang.Integer getCodigo();
public void setCodigo(java.lang.Integer);
}
[/sourcecode]

$javap -p AlumnoGroovy

[sourcecode language='java']
Compiled from "AlumnoGroovy.Groovy"
public class AlumnoGroovy extends java.lang.Object implements groovy.lang.GroovyObject{
public static final java.lang.Class $ownClass;
private java.lang.String nombre;
private java.lang.Integer codigo;
private static org.codehaus.groovy.reflection.ClassInfo $staticClassInfo;
private transient groovy.lang.MetaClass metaClass;
public static java.lang.Long __timeStamp;
public static java.lang.Long __timeStamp__239_neverHappen1246636547916;
private static java.lang.Class $class$java$lang$Class;
private static java.lang.Class $class$groovy$lang$MetaClass;
private static java.lang.Class $class$AlumnoGroovy;
private static java.lang.ref.SoftReference $callSiteArray;
public AlumnoGroovy();
protected groovy.lang.MetaClass $getStaticMetaClass();
public groovy.lang.MetaClass getMetaClass();
public void setMetaClass(groovy.lang.MetaClass);
public java.lang.Object invokeMethod(java.lang.String, java.lang.Object);
public java.lang.Object getProperty(java.lang.String);
public void setProperty(java.lang.String, java.lang.Object);
static {};
public java.lang.String getNombre();
public void setNombre(java.lang.String);
public java.lang.Integer getCodigo();
public void setCodigo(java.lang.Integer);
public void super$1$wait();
public java.lang.String super$1$toString();
public void super$1$wait(long);
public void super$1$wait(long, int);
public void super$1$notify();
public void super$1$notifyAll();
public java.lang.Class super$1$getClass();
public boolean super$1$equals(java.lang.Object);
public java.lang.Object super$1$clone();
public int super$1$hashCode();
public void super$1$finalize();
private static java.lang.Class $get$$class$java$lang$Class();
private static java.lang.Class $get$$class$groovy$lang$MetaClass();
private static java.lang.Class $get$$class$AlumnoGroovy();
static java.lang.Class class$(java.lang.String);
private static org.codehaus.groovy.runtime.callsite.CallSiteArray $createCallSiteArray();
private static org.codehaus.groovy.runtime.callsite.CallSite[] $getCallSiteArray();
}
[/sourcecode]

Como ven el archivo groovy tiene todo lo que tiene la clase java, esto quiere decir que una vez que tienes compilada la clase groovy, otras clases java pueden utlizarlas como si hubiera sido escrito en codigo java. Pero no voy a quedar con una especulacion y a continuación probaremos que esto es cierto.

Creamos una clase que servirá para probar lo dicho anteriormente:

[sourcecode language='java']
public class CrearAlumnoJava{
public static void main(String agrs[]){
/**Con Java**/
Alumno al= new Alumno();
al.setNombre("Edwin Farfan");
al.setCodigo(1234);
System.out.println("Alumno Creado con Java: "+ al.getNombre());

/**Con Groovy**/
AlumnoGroovy ag=new AlumnoGroovy();
ag.setNombre("Jose Diaz");
ag.setCodigo(5678);
// en el .groovy no hay definido un set pero sin embargo se puede llamarlo.
System.out.println("Alumno Creado con Groovy: "+ ag.getNombre());
}
}

[/sourcecode]

Ejecutamos la clases CrearAlumnoJava con el sgte codigo:
java -classpath $GROOVY_HOME/embeddable/groovy-all-1.6.3.jar:. CrearAlumnoJava

y el resultado será el sgte:
Alumno Creado con Java: Edwin Farfan
Alumno Creado con Groovy: Jose Diaz

Listo ya hemos probado que Groovy se puede ejecutar en una clase java comun y corriente.
Ahora vamos hacer lo mismo pero con Groovy.

[sourcecode language='java']
class CrearAlumnoGroovy{

public static void main(String []agrs){
/*con Java*/
def al=new Alumno(nombre:"Edwin", codigo:1234)
println "Nombre del Alumno Java: " + al.nombre

/*con Groovy*/
def ag=new AlumnoGroovy(nombre:"joedayz", codigo:5678)
println "Nombre del Alumno Groovy: "+ag.nombre
}
}
[/sourcecode]

Fijense como llamo a la Clase Alumno en el propio archivo groovy, esto demuestra que se puede llamar un .java llama desde un .groovy, tambien hay que resaltar algo nuevo la variabe 'def', que no es más que una variable dinámica (la van a ver bastante), aqui en este ejemplo no hay necesidad del ";", si queremos podemos decir por ejemplo "ag.getNombre()" en lugar de "ag.nombre", esto no variaría en lo absoluto el resultado.

Compilamos el archivo de groovy:
$ groovyc CrearAlumnoGroovy.groovy

y lo ejecuto:
$ groovy CrearAlumnoGroovy

mostrará el sgte resultado:
Nombre del Alumno Java: Edwin
Nombre del Alumno Groovy: joedayz

Con esto hemos demostrado la integracion de Groovy con Java es perfecta, con pequeños ejemplos hemos rozado la superficie de Groovy, espero que esto les sirva para que se adentren mas sobre el tema.

Espero que haya comentarios y preguntas sobre el tema.

Saludos .
Ahhh se me olvidaba aqui les dejo el Codigo Fuente

1 comentario:

Christian Komiya dijo...

Bien doc, (Y)

me vacila la parte que dice:

Alumno Creado con Java: Edwin Farfan

jeje.

Saludos.