miércoles, 17 de febrero de 2010

Ordenar elementos de List en java con Collections.sort

Hola:

Todos alguna vez nos topados con ordenar elementos de una List de java (java.util.List) yo se que muchos van a decir que se podria hacer con la base de datos agregando un order by campo_de_tbl, pero muchas aplicaciones no lo requieren y para lograr esto ocuparemos java.util.Comparator.

Paso 1. Crear un bean, para fines prácticos todos los atributos serán String :

public class Concepto {

private String id;
private String cve;
private String descripcion;
private String valor;


public String getValor() {
return valor;
}
public void setValor(String valor) {
this.valor = valor;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getCve() {
return cve;
}
public void setCve(String cve) {
this.cve = cve;
}
public String getDescripcion() {
return descripcion;
}
public void setDescripcion(String descripcion) {
this.descripcion = descripcion;
}



}

Supongamos que queremos ordenas nuestros datos de nuestra List atravez del atributo cve.

Paso 2. Crear la clase que ConceptoComparator que implementa la interfaz Comparator

import java.util.Comparator;


public class ConceptoComparator implements Comparator{

public int compare(Object arg0, Object arg1) {
Concepto conA = (Concepto) arg0;
Concepto conB=(Concepto)arg1;

Long cveConA = Long.parseLong(conA.getCve());
Long cveConB = Long.parseLong(conB.getCve());

if(cveConA < cveConB)
return -1;

else
if (cveConA > cveConB)
return 1;


return 0;
// TODO Auto-generated method stub

}

}

java.util.Comparator int compare(T a, T b) compara dos objetos y proporciona un valor negativo si a va antes que b, cero si se consideran idénticos en el orden de clasificación, y un valor positivo si a va después de b.

Paso 3 : llamar al metodo Collections.sort(...)

List conceptos = new ArrayList();

Concepto con1 = new Concepto();
con1.setCve("10017");

Concepto con2 = new Concepto();
con2.setCve("20001");

Concepto con3 = new Concepto();
con3.setCve("10001");

conceptos.add(con1);
conceptos.add(con2);
conceptos.add(con3);
System.out.println("sin ordenar ");

for(Concepto con : conceptos){
System.out.println(" "+con.getCve());
}

Collections.sort(conceptos, new ConceptoComparator());

System.out.println("ordenados ");
for(Concepto con : conceptos){
System.out.println(" "+con.getCve());
}


el resultado sera algo como esto:
sin ordenar
10017
20001
10001
ordenados
10001
10017
20001

martes, 2 de febrero de 2010

Md5 en java (java.security.MessageDigest)

Hola aquí pongo un código que estaba buscando hace tiempo ocupando la API (java.security.MessageDigest) de java para encriptar una cadena.

----------------------


import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

public class Md5 {

private MessageDigest alg;
private String md5;


/**
*
* @param mensaje
* @throws NoSuchAlgorithmException
*/

public void md5(String mensaje) throws NoSuchAlgorithmException{
alg = MessageDigest.getInstance("MD5");//implementa el algoritmo especificado
byte[] bytes = mensaje.getBytes();
computeDigest(bytes);
}


public String getMd5() {
return md5;
}


public void setMd5(String md5) {
this.md5 = md5;
}
/**
* Realiza la digestion del algoritmo MD5
* @param bytes
*/

public void computeDigest(byte[] bytes){
String cad="";
alg.reset();//restaura el resumen
alg.update(bytes);//actualiza el resumen, empleando los bytes especificados
byte[] hash = alg.digest();//completa el calculo del codigo de dispersivo
for(int i = 0; i < hash.length;i++){
int v = hash[i] & 0xFF;
if(v < 16) cad+="0";
cad+=Integer.toString(v,16).toUpperCase()+"";
}

this.setMd5(cad);
}


}

----------------------------------------------------

La manera de ocupar la clase seria la siguiente:

Md5 md5 = new Md5();
md5.md5("Hola mundo");
String md5String = md5.getMd5();
System.out.print(" md5 "+md5String);

lunes, 1 de febrero de 2010

RCP en Gwt (Netbeans gwt-ext)

Hola:

Para esta entrada es necesario que tengan configurado previamente un proyecto con gwt en Netbeans y también configurado en plugin de gwt-ext (jar).

Primero me gustaría hablar de las ventajas de Gwt y después hablar de las desventajas.

- Todo lo programas en Back End, lo que quiere decir que no tienes que aprender forzosamente html, css, javaScript solo tienes que saber java, el Front End lo programas en Back End aunque suene extraño asi es, el compilador de gwt se encarga de generar un codigo optimo en js para tu aplicación.

- La manera de hacer peticiones asíncronas se hacen de manera rápida por medio de RCP.

- La curva de aprendizaje es rápida.

- Las aplicaciones funcionan en la mayoría de los navegadores (IE,Firefox).

Bueno después de esta breve introducción vamos a crear una aplicación que de administre usuarios un CRUD.

Paso 1: Como siempre crear un bean que es parte del modelo para este ejemplo se llamara el clásico usuario, es muy importante que lo coloquen en el paquete donde van a poner su Gwt Modulo.

Para nuestro ejemplo tendremos que crear nuestro paquete del modelo y view al nivel de: org.aplication.client donde va todo en codigo que se convierte en Front End.

Despues creamos un clase de llamada Usuario dentro del paquete org.aplication.client.modelo


Creamos una clase llamada Usuario.

package org.aplication.client.modelo;

import com.google.gwt.user.client.rpc.IsSerializable;

/**
*
* @author isaac
*/
public class Usuario implements IsSerializable{

private String nombre;
private String apellido;
private int edad;
private int cve;

public String getApellido() {
return apellido;
}

public void setApellido(String apellido) {
this.apellido = apellido;
}

public int getCve() {
return cve;
}

public void setCve(int cve) {
this.cve = cve;
}

public int getEdad() {
return edad;
}

public void setEdad(int edad) {
this.edad = edad;
}

public String getNombre() {
return nombre;
}

public void setNombre(String nombre) {
this.nombre = nombre;
}



}

Esta clase implementa IsSerializable de gwt que es la que encargara de serializar nuestra clase y permite la comunicación entre en cliente y el servidor.

Paso 2. Creamos un paquete llamado view (org.aplication.client.view) y una clase llamada GuiUsuario, el diagrama de clase Uml para esta clase sera mas o menos como este aunque despues iremos agregando mas metodos o clases.



Bueno primero crearemos nuestro formulario y despues nuestro rcp.


package org.aplication.client.view;

import com.gwtext.client.core.EventObject;
import com.gwtext.client.core.Position;
import com.gwtext.client.widgets.Button;
import com.gwtext.client.widgets.MessageBox;
import com.gwtext.client.widgets.Window;
import com.gwtext.client.widgets.event.ButtonListenerAdapter;
import com.gwtext.client.widgets.form.FormPanel;
import com.gwtext.client.widgets.form.TextField;
import org.aplication.client.modelo.Usuario;

/**
*
* @author isaac
*/
public class GuiUsuario {

private Usuario usuario;
private Window window;
private FormPanel formPanel;
private TextField nombre;
private TextField apellido;
private TextField edad;

public FormPanel getFormPanel() {
formPanel = new FormPanel();
formPanel.setFrame(true);
formPanel.setTitle("Usuario");
nombre = new TextField("Nombre", "nombre", 230);
apellido = new TextField("Apellido", "apellido", 230);
edad = new TextField("Edad", "edad", 230);
formPanel.add(nombre);
formPanel.add(apellido);
formPanel.add(edad);
return formPanel;

}

public Usuario getUsuario() {
return usuario;
}
public Window getWindow() {
window = new Window();
window.setTitle("Layout Window");
window.setClosable(true);
window.setWidth(600);
window.setHeight(350);
window.setPlain(true);
window.setCloseAction(Window.HIDE);
window.add(getFormPanel());

Button buttonNewUser = new Button("Nuevo Usuario"); buttonNewUser.addListener(new ButtonListenerAdapter(){
@Override public void onClick(Button button, EventObject e) {

MessageBox.alert("prueba de evento");


}
} ); window.setButtonAlign(Position.CENTER);
window.addButton(buttonNewUser); return window; }

public void setUsuario(Usuario usuario) {
this.usuario = usuario;
}



}

El metodo getWindow() se encarga de crear la ventana y tambien de crear el FormPanel por medio del metodo getFormPanel(), despues solo hace falta llamar a nuestra Gui desde el EntryPoint que sera la clase MainEntryPoint que esta en el paquete org.aplication.client.


package org.aplication.client;

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.Widget;
import com.google.gwt.user.client.ui.ClickListener;
import com.gwtext.client.widgets.Window;
import org.aplication.client.view.GuiUsuario;

/**
* Main entry point.
*
* @author isaac
*/
public class MainEntryPoint implements EntryPoint {
/**
* Creates a new instance of MainEntryPoint
*/
public MainEntryPoint() {
}

/**
* The entry point method, called automatically by loading a module
* that declares an implementing class as an entry-point
*/
public void onModuleLoad() {

final Button button = new Button("Click me!");

button.addClickListener(new ClickListener(){
public void onClick(Widget w) {
GuiUsuario guiUsuario = new GuiUsuario();
Window winUsu = guiUsuario.getWindow();
winUsu.show();
}
});

RootPanel.get().add(button);

}
}



winUsu.show(); Este metodo de la clase Window hace que la ventana se visualize en el navegador del cliente.

Depues damos run a proyecto y deberiamos tener algo como esto.



Paso 3. Crear el RCP damos click derecho en new / other depues aparecera la opcion de gwt y una lista donde esta gwtrcp damos click y despues nos pedira en nombre del servicio en paquete donde lo pondremos.


Creación del servio: Lo llamaremos GWTServiceUser y estará dentro del paquete org.aplication.client.servicio

Después tendremos una estructura como la siguiente:


Un rcp de gwt necesita de 3 clases principales y un mapeo en el web.xml que ya hace por defecto el ayudante de netbeans.

dentro del paquete org.aplication.client.servicio
- interface GWTServiceUserAsync
-interface GWTServiceUser
y del lado del servidor en el paquete org.aplication.server.servicio esta la clase:
-class GWTServiceUserImpl

El diagrama de clases para la creación de usuarios desde el cliente al servidor es la siguiente:

El código para cada clase es el siguiente:

package org.aplication.client.servicio;

import com.google.gwt.user.client.rpc.RemoteService;
import com.google.gwt.user.client.rpc.RemoteServiceRelativePath;
import org.aplication.client.modelo.Usuario;

/**
*
* @author isaac
*/
@RemoteServiceRelativePath("servicio/gwtserviceuser")
public interface GWTServiceUser extends RemoteService {
public String nuevoUsuario(Usuario usuario);
}

---------------

package org.aplication.client.servicio;

import com.google.gwt.user.client.rpc.AsyncCallback;
import org.aplication.client.modelo.Usuario;

/**
*
* @author isaac
*/
public interface GWTServiceUserAsync {
public void nuevoUsuario(Usuario usuario, AsyncCallback callback);
}

--------------------------------------

package org.aplication.server.servicio;

import com.google.gwt.user.server.rpc.RemoteServiceServlet;

import java.util.AbstractList;
import java.util.ArrayList;
import java.util.List;
import org.aplication.client.modelo.Usuario;
import org.aplication.client.servicio.GWTServiceUser;

/**
*
* @author isaac
*/


public class GWTServiceUserImpl extends RemoteServiceServlet implements GWTServiceUser {

private static List usuarios = null;
private static int contCve = 0;

public String nuevoUsuario(Usuario usuario) {
contCve++;
usuario.setCve(contCve);

if(usuarios==null){

usuarios = new ArrayList();
usuarios.add(usuario);

}else
usuarios.add(usuario);

for(Usuario u:usuarios){
System.out.println("usuario "+u.getNombre());
}

return "Se ha creado el usuario";
}




}

-------------------------------------------------------------


package org.aplication.client.view;

import com.google.gwt.core.client.GWT;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.rpc.ServiceDefTarget;
import com.gwtext.client.core.EventObject;
import com.gwtext.client.core.Position;
import com.gwtext.client.widgets.Button;
import com.gwtext.client.widgets.MessageBox;
import com.gwtext.client.widgets.Window;
import com.gwtext.client.widgets.event.ButtonListenerAdapter;
import com.gwtext.client.widgets.form.FormPanel;
import com.gwtext.client.widgets.form.TextField;
import org.aplication.client.modelo.Usuario;
import org.aplication.client.servicio.GWTServiceUser;
import org.aplication.client.servicio.GWTServiceUserAsync;

/**
*
* @author isaac
*/
public class GuiUsuario {

private Usuario usuario;
private Window window;
private FormPanel formPanel;
private TextField nombre;
private TextField apellido;
private TextField edad;
private static GWTServiceUserAsync service;

public FormPanel getFormPanel() {


formPanel = new FormPanel();
formPanel.setFrame(true);
formPanel.setTitle("Usuario");
nombre = new TextField("Nombre", "nombre", 230);
apellido = new TextField("Apellido", "apellido", 230);
edad = new TextField("Edad", "edad", 230);
formPanel.add(nombre);
formPanel.add(apellido);
formPanel.add(edad);


return formPanel;
}

public Usuario getUsuario() {
return usuario;
}

public Window getWindow() {

window = new Window();
window.setTitle("Layout Window");
window.setClosable(true);
window.setWidth(600);
window.setHeight(350);
window.setPlain(true);
window.setCloseAction(Window.HIDE);
window.add(getFormPanel());

Button buttonNewUser = new Button("Nuevo Usuario");
buttonNewUser.addListener(new ButtonListenerAdapter(){

@Override
public void onClick(Button button, EventObject e) {
Usuario u = new Usuario();
u.setEdad(Integer.parseInt(edad.getText()));
u.setNombre(nombre.getText());
u.setApellido(apellido.getText());

insertaUsuario(u);

}

}
);


window.setButtonAlign(Position.CENTER);
window.addButton(buttonNewUser);



return window;
}

public void setUsuario(Usuario usuario) {
this.usuario = usuario;
}



public void insertaUsuario(Usuario usuario) {


// Create an asynchronous callback to handle the result.
final AsyncCallback callback = new AsyncCallback() {

public void onSuccess(Object result) {
String respuesta = (String) result;

MessageBox.alert(respuesta);

}

public void onFailure(Throwable caught) {
MessageBox.alert("Error " + caught);
}
};

getService().nuevoUsuario(usuario, callback);

}


public static GWTServiceUserAsync getService() {
service = (GWTServiceUserAsync) GWT.create(GWTServiceUser.class);
ServiceDefTarget endpoint = (ServiceDefTarget) service;
String moduleRelativeURL = GWT.getModuleBaseURL() + "servicio/gwtserviceuser";
endpoint.setServiceEntryPoint(moduleRelativeURL);
return service;
}



}

----------------------------------------

- La parte importante que debemos entender de los rcp de gwt es que podemos mandar beans desde los clientes hasta nuestro servidor de manera clara sin necesidad de ocupar
request.

La menera que se logra esto es atravez de del siguiente metodo de la clase
GuiUsuario.

public static GWTServiceUserAsync getService() {
service = (GWTServiceUserAsync) GWT.create(GWTServiceUser.class);
ServiceDefTarget endpoint = (ServiceDefTarget) service;
String moduleRelativeURL = GWT.getModuleBaseURL() + "servicio/gwtserviceuser";
endpoint.setServiceEntryPoint(moduleRelativeURL);
return service;
}

y para llamarlo ocupamos el metodo siguiente dentro de la misma clase:

public void insertaUsuario(Usuario usuario) {

// Create an asynchronous callback to handle the result.
final AsyncCallback callback = new AsyncCallback() {
public void onSuccess(Object result) {
String respuesta = (String) result;

MessageBox.alert(respuesta);

}

public void onFailure(Throwable caught) {
MessageBox.alert("Error " + caught);
}
};

getService().nuevoUsuario(usuario, callback);

}

Cuando se ejecuta este metodo llama directemente a metodo getService() el cual tiene un metodo llamado nuevoUsuario que ha este le mandamos como parametro el usuario y el callback que su tarea va ser recibir la respuesta del rcp del servidor en este caso de la clase GWTServiceUserImpl que sobreescribe el método nuevoUsuario que es donde creamos la lista y insertamos elementos a ella y esta responde con el mensaje return "Se ha creado el usuario" el cual es recibido por el callback en:

public void onSuccess(Object result) {
String respuesta = (String) result;

MessageBox.alert(respuesta);
.
.
.

Por ultimo necesitamos el evento del boton de la GuiUsuario para crear el usuario y llamar al método insertaUsuario

Button buttonNewUser = new Button("Nuevo Usuario");
buttonNewUser.addListener(new ButtonListenerAdapter(){

@Override
public void onClick(Button button, EventObject e) {
Usuario u = new Usuario();
u.setEdad(Integer.parseInt(edad.getText()));
u.setNombre(nombre.getText());
u.setApellido(apellido.getText());

insertaUsuario(u);

}

}
);

Después damos run al proyecto y nuestra aplicación esta lista para crear usuarios yo puse una lista estática de usuarios pero bien se pueden insertar en una base de datos con hibernate o con jdbc.


Bueno eso es todo despues crearemos un grid ....

Dedicado a mi princesita.


Segunda Parte