viernes, 23 de abril de 2010

Reportes en Excel con JexcelApi

Siempre existe la duda entre los desarrolladores java, de como empezar a tratar documentos Excel desde el lenguaje Java. Sea en la lectura o escritura de los mismos.
El uso masivo de archivos e informes en excel en las distintas empresas.. obligan al desarrollador estar en la capacidad de emitir reportes en excel desde una aplicación Java. Esto permitirá poder combinar la capacidad de información de una base de datos en una presentación amigable y conocida como son los archivos Excel.
Es por ello, la necesidad de dar a conocer JexcelApi  una poderosa herramienta, muy útil para manejar los parámetros y valores de la conocida hoja Excel desde un programa Java. También es necesario dar a conocer que existe el proyecto Jakarta POI para el tratamiento de archivos en formato microsoft.


excel.jpg


JavaEE con JExcelApi - jxl

Para empezar a usar jexcel desde java .. tendremos que colocar la librería jxl.jar a nuestro aplicativo. Dicha librería la podemos descargar desde sourceforge.net . Personalmente recomiendo usar esta API antes que POI para el tratamiento de archivos excel.

Veremos la sintaxis de uso .. mediante un ejemplo de escritura de excel bastante simple.

log.info("Entrando ... reporteCertificados()");
  
  OutputStream out = null;

  try{

   res.setContentType("application/vnd.ms-excel");
   res.setHeader("Content-disposition", "attachment; filename=\"ParaCertificados.xls\"");
   res.setHeader("Content-type", "application/vnd.ms-excel");
   
   //ini:formato
   WritableFont cabeceraFont = new WritableFont(WritableFont.ARIAL, 10, WritableFont.BOLD, true);
   WritableFont cuerpoFont = new WritableFont(WritableFont.ARIAL, 10, WritableFont.NO_BOLD, false);
   WritableFont domicilioFont = new WritableFont(WritableFont.ARIAL, 9, WritableFont.NO_BOLD, false); 
   
   WritableCellFormat fCabecera = new WritableCellFormat(cabeceraFont);
   fCabecera.setAlignment(Alignment.JUSTIFY);
   fCabecera.setVerticalAlignment(VerticalAlignment.CENTRE);
   fCabecera.setBackground(Colour.CORAL);
   fCabecera.setBorder(Border.ALL,BorderLineStyle.THIN);
   
   WritableCellFormat fCuerpo = new WritableCellFormat(cuerpoFont);
   fCuerpo.setAlignment(Alignment.LEFT);
   fCuerpo.setBorder(Border.ALL,BorderLineStyle.THIN);
   
   WritableCellFormat fCuerpo2 = new WritableCellFormat(domicilioFont);
   fCuerpo2.setAlignment(Alignment.LEFT);
   fCuerpo2.setBorder(Border.ALL,BorderLineStyle.THIN);
   
   //fin:formato
   
   WritableWorkbook w = Workbook.createWorkbook(res.getOutputStream());
   WritableSheet s = w.createSheet("Informe", 0); //Nombre de hoja

   s.setColumnView(0,10);//ini:seteamos el ancho de las columnas 
   s.setColumnView(1,20);
   s.setColumnView(2,20);
   s.setColumnView(3,20);
   s.setColumnView(4,25);
   s.setColumnView(5,10);
   s.setColumnView(6,15);
   s.setColumnView(7,15);
   s.setColumnView(8,10);
   s.setColumnView(9,10);
   s.setColumnView(10,30);
   s.setColumnView(11,20);
   s.setColumnView(12,20);

  //ini: armando el excel
   s.addCell(new Label(0, 0, "Nº",fCabecera)); //añadiendo celdas
   s.addCell(new Label(1, 0, "Nro. Certificado",fCabecera));
   s.addCell(new Label(2, 0, "Apellido Paterno",fCabecera));
   s.addCell(new Label(3, 0, "Apellido Materno",fCabecera));
   s.addCell(new Label(4, 0, "Nombres",fCabecera));
   s.addCell(new Label(5, 0, "DNI",fCabecera));
   s.addCell(new Label(6, 0, "Fecha Inicio",fCabecera));
   s.addCell(new Label(7, 0, "Fecha Fin",fCabecera));
   s.addCell(new Label(8, 0, "Año",fCabecera));
   s.addCell(new Label(9, 0, "Horas",fCabecera));
   s.addCell(new Label(10, 0, "Región",fCabecera));   
 
   List<map> lstData = serviceFactory.getReporteService().getDataReporte(Long.valueOf(IdTaller));
   
   int i=1;
   for(Map map:lstData){
    s.addCell(new Number(0,i, Integer.parseInt(map.get("ORDEN").toString()),fCuerpo));
    s.addCell(new Label(1, i, StringUtils.EMPTY,fCuerpo));
    s.addCell(new Label(2, i, map.get("APE_PAT").toString(),fCuerpo));
    s.addCell(new Label(3, i, map.get("APE_MAT").toString(),fCuerpo));
    s.addCell(new Label(4, i, map.get("NOMBRES").toString(),fCuerpo));
    s.addCell(new Label(5, i, map.get("DNI").toString(),fCuerpo));
    s.addCell(new Label(6, i, map.get("DIA_INI").toString()+ " de "+Utils.getMesLetras(new Integer(map.get("MES_INI").toString())) ,fCuerpo));
    s.addCell(new Label(7, i, map.get("DIA_FIN").toString()+ " de "+Utils.getMesLetras(new Integer(map.get("MES_FIN").toString())),fCuerpo));
    s.addCell(new Label(8, i, map.get("ANIO").toString(),fCuerpo));
    s.addCell(new Label(9, i, map.get("HORAS").toString(),fCuerpo));
    s.addCell(new Label(10, i, map.get("REGION").toString(),fCuerpo2));

    i++;
   }
   //fin:armando el excel
   
   w.write();
   w.close();
   
   
  } catch (Exception ex) {
   log.error(ex.getMessage(),ex);
   sendErrorMessage(req,"errors.excel.load");
  } finally {
   if (out != null)
       out.close();  
  }

  log.info("Saliendo ... reporteCertificados() - Reportes");
return null;




Para Profundizar en el Tema

Bueno espero que les sirva la información proporcionada ... se despide su amigo edisonjc7.. y como dice un amigo ... "seguiremos socializando el conocimiento" xD... chau

viernes, 16 de abril de 2010

Procedures y Cursores en Mysql

Un Stored Procedure o Procedimiento Almacenado es un programa (o función) que se almacena físicamente en una base de datos.Su implementación varía de un manejador de bases de datos a otro. En la mayoría de los casos, no obstante, los stored procedures permiten definir una API (capa de abstracción) para que el gestor de bases de datos interactúe con tablas u otros objetos de la base de datos, en vez de tener un cliente de la aplicación interactuando directamente.
Aunque la mayoría de los gestores de bases de datos existentes brindan soporte para estos procedimientos, existe discusión entre los desarrolladores acerca de las ventajas de su uso.
Por eso empezaremos este post definiendo las ventajas y desventajas del uso de Stored Procedures.
Cabe mencionar que el uso de procedimientos almacenados depende muchas veces de la arquitectura del sistema y del alcance del mismo.

db-java.jpg

Ventajas

Es notorio que existen más ventajas que desventajas en el uso de procedimientos.

  • Es ejecutado directamente en el motor de bases de datos, el cual usualmente corre en un servidor separado. Como tal, posee acceso directo a los datos que necesita manipular y sólo necesita enviar sus resultados de regreso al usuario, deshaciéndose de la sobrecarga resultante de comunicar grandes cantidades de datos salientes y entrantes.

  • Encapsulamiento de un proceso complejo o que podría requerir la ejecución de varias consultas SQL, tales como la manipulación de un gran conjunto de datos para producir un resultado resumido. Esto reduce la necesidad de codificar lógica innecesaria en el programa cliente y tener un mejor manejo de la capa de negocio de nuestra aplicación.

  • Centralización de la definición, al formar parte de la base de datos los procedimientos almacenados están en un lugar centralizado y pueden ser ejecutados por cualquier aplicación que tenga acceso a la misma. Evitando la excesiva declaración de procedimientos de ejecución en el gestor de bases de datos; ya que puede ser perjudicial para el rendimiento del servidor.

  • Reducción del tráfico de red, una sentencia formada por decenas, cientos o incluso miles de líneas de código SQL puede escribirse como un procedimiento almacenado en el servidor y ejecutarse simplemente mediante el nombre de dicho procedimiento.
Desventajas

Como lo mencione en un principio el uso de los procedures depende mucho de la arquitectura y alcance del sistema. En una arquitectura multi-base de datos en donde la información deberá ser manejada en distintos motores de base de datos sea MySql, Postgresql, Oracle, Sql Server, etc.O en una arquitectura en donde querramos migrar después a otro motor de base de datos. No conviene el uso de procedures de ninguna manera.


  • Reducción de la escalabilidad: Los procedimientos almacenados nos esclavizan al motor de base de datos. Para migrar de un gestor de base de datos con muchos procedimientos almacenados a otro, se deberá reescribir casi la totalidad de los mismos. Esto se debe, principalmente, a que los lenguajes de procedimientos almacenados de distintos fabricantes no son compatibles entre sí.

Teniendo en cuenta las ventajas y desventajas es aconsejable no abusar de los procedimientos almacenados y utilizarlos sólo cuando su aplicación sea realmente efectiva y el alcance del sistema este bien definido. Con respecto al uso de los procedures siempre habrá controversia entre los desarrolladores.


Implementación y Sintaxis en Mysql 5

Desde MySQL 5 los procedimientos almacenados empezaron a ser soportados.
Son implementados desde la aplicación mediante CALL nombre_procedure (…parametros).

Voy a poner un par de ejemplos definiendo la sintaxis de creación de un procedure y dentro de él el uso de cursores en mysql. La finalidad de estos procedures es lo de menos, lo que nos interesa es la sintaxis para poder desarrollar nuestros propios procedimientos, con lógica a medida de nuestras necesidades.

Nota: El uso del cursor sirve para recorrer uno por uno los registros del resultado de la select y poder hacer operaciones con ella. Es como recorrer una lista con un for java y hacer operaciones con cada registro.


Ejemplo 1.- Definimos un procedure con 2 parámetros de entrada, variables que nos permitirán el desarrollo de nuestra lógica, el cursor que nos permitirá recorrer uno a uno el resultado de la select, y el retorno de una cadena que será procesada posteriormente por el programa cliente.

-- en esta línea eliminamos el procedure de la base de datos si existe.
DROP PROCEDURE IF EXISTS `nombreBD`.`cur_pagination_SP`;
DELIMITER \\

--definiendo la creación del procedure con 2 parametros de entrada 
CREATE PROCEDURE `nombreBD`.`cur_pagination_SP` ( IN v_id_taller INTEGER,
                                                  IN v_pagination INTEGER )
    READS SQL DATA
BEGIN
--declaración de variables
DECLARE l_last_row INT DEFAULT 0;
DECLARE v_ape_pat VARCHAR(255);
DECLARE contador int default 0;
DECLARE rpt VARCHAR(300) default '';

--declaración del cursor de nombre ´cursor1´
DECLARE cursor1 CURSOR FOR
SELECT u.ape_pat 
FROM tb_usuario u
WHERE NOT EXISTS (
       SELECT * FROM tb_cabecera ci
       WHERE  u.id_usuario = ci.id_usuario and 
              ci.id_capacitacion = v_id_taller
) AND u.is_deleted !=1 and u.perfil in ('E','D')
ORDER BY u.ape_pat ASC;

--Flag que permitirá saber si existen más registros por recorrer
DECLARE CONTINUE HANDLER FOR NOT FOUND SET l_last_row=1;

--abrimos el cursor para empezar a recorrerlo
OPEN cursor1;
c1_loop: LOOP
    -- cada registro se le otorga a la variable 'v_ape_pat'
    FETCH cursor1 INTO v_ape_pat;
        IF (l_last_row=1) THEN
            LEAVE c1_loop;
        END IF;

        --lógica propia de este procedure
        if contador%v_pagination = 0 then
          SET rpt = CONCAT(rpt,substring(v_ape_pat,1,1));
        end if;

        SET contador = contador + 1;

END LOOP c1_loop;

--cerramos el cursor y retornamos el dato que nos interesa en este caso la variable 'rpt'
CLOSE cursor1;
SELECT rpt;

END\\
DELIMITER;



Ejemplo 2.- A diferencia del primer ejemplo veremos como crear dos cursores dentro del mismo procedure.

DROP PROCEDURE IF EXISTS `nombreBD`.`porcentaje_SIS_CAP`;
DELIMITER \\

CREATE PROCEDURE `nombreBD`.`porcentaje_SIS_CAP` ( IN v_id_cabecera INTEGER)
    READS SQL DATA
BEGIN

DECLARE l_last_row INT DEFAULT 0;
DECLARE v_cantidad INT DEFAULT 0;
DECLARE v_total INT DEFAULT 0;
DECLARE v_nota VARCHAR(5) default '';
DECLARE rpt VARCHAR(150) default '';

--declaración del primer cursor
DECLARE cur_total CURSOR FOR
SELECT
    COUNT(*) AS 'CANTIDAD'
FROM tb_cabecera a
INNER JOIN tb_inscripcion c ON a.id_cabecera=c.id_cabecera
WHERE a.id_cabecera = v_id_cabecera
GROUP BY c.nota;

--declaración del segundo cursor
DECLARE cur_calculo CURSOR FOR
SELECT
    c.nota_evalua  AS "NOTA",COUNT(*) AS 'CANTIDAD'
FROM tb_cabecera a
INNER JOIN tb_inscripcion c ON a.id_cabecera=c.id_cabecera
WHERE a.id_cabecera = v_id_cabecera
GROUP BY c.nota
ORDER BY c.nota_evalua ASC;

DECLARE CONTINUE HANDLER FOR NOT FOUND SET l_last_row=1;

OPEN cur_total;
REPEAT
    FETCH cur_total INTO v_cantidad;
    IF not l_last_row THEN
       SET v_total = v_total + v_cantidad;
    END IF;   
UNTIL l_last_row END REPEAT;

CLOSE cur_total;

SET v_cantidad = 0;
set l_last_row = 0;

OPEN cur_calculo;
c2_loop: LOOP
    FETCH cur_calculo INTO v_nota,v_cantidad;
    IF l_last_row THEN
        LEAVE c2_loop;
    END IF;
SET rpt = CONCAT(rpt,'&',v_nota,'-',v_cantidad,'-',(v_cantidad/v_total)*100,'-',v_total);

END LOOP c2_loop;
CLOSE cur_calculo;

SELECT rpt;

END\\
DELIMITER;


Espero que les pueda servir este post para la mejor toma de decisiones, al momento de definir la arquitectura de su aplicación. Saludos a todos.... se despide su amigo edisonjc7 .. no sin antes dejarles un regalillo para los amantes del mysql .. jeje xD..

Un regalillo para todos los seguidores de Mysql

La biblia del Mysql - Download

Manual de Referencia en Español - Download


jueves, 8 de abril de 2010

Desarrollador Java Certificado por Sun Microsystems - SCJP

Empezare este post planteando la siguiente pregunta : ¿Para qué nos sirve esta certificación? ...

Java es el lenguaje de moda, todas las empresas están reclutando analistas/programadores en Java. Hace algunos años no había mucha gente con estos conocimientos, por lo que colocarse en el mundo laboral era relativamente fácil. Ahora hay mucha gente preparada y esta certificación puede diferenciar tu Hoja de Vida frente a la de los demás.

Además el hecho de prepararse para esta certificación te dará nuevos conocimientos y te permitirá acreditar esos conocimientos con un cartón.

En resumen, la certificación Java junto con un buen currículum te otorgará la llave para realizar muchas entrevistas de trabajo, y acceder a un buen salario.



Por dónde empezar?

  • Primero adquirir el voucher .- Es un documento digital, que tiene un número que lo identifica, cuando adquieres el voucher lo único que interesa es dicho número. En el Perú te puedes contactar con la empresa CJAVA, un asociado de negocios de Sun, para adquirir tu voucher. Se sabe que el costo normal  del voucher es de 300$ según la web de Sun; pero aveces existen promociones, como ejemplo puedo indicar que accedí a un voucher con la opción retake(doble) por la suma de 150$. Es por ello la importancia de ponerse en contacto con CJAVA. email de contacto: elizabeth.bazalar@cjavaperu.com

  • Registrarse en Prometric.- Una vez que accedes al código del voucher, tienes que registrarte y programar tu examen en la web de Prometric (Centro para la aplicación de exámenes de Certificación Internacional en Tecnologías).

  • Rendir el examen.- Vas a la institución donde has programado el examen 30 minutos antes con tu DNI, firmas algunos documentos que indican las politicas del examen y al culminar te entregan tu reporte que indica si has aprobado o no y los temas del examen con un porcentage de evaluación sobre cada uno de ellos.

  • Solo Si aprobaste deberás validar tu dirección desde CertManager para que te envíen el certificado. Por último solo te queda esperar el certificado xD.

Cómo Prepararme?
Primero debes tener en cuenta que el SCJP es requisito para todas las demás certificaciones Java. Por ello su obtención es crucial. Código del examen 310-055 ó 310-065.


Libros altamente Recomendables.
Para rendir el examen deberás conocer los siguientes aspectos:
  • Language Fundamentals
  • Declarations and Access Control
  • Object Orientation
  • Assignments
  • Operators
  • Flow Control, Exceptions, and Assertions
  • Strings, I/O, Formatting, and Parsing
  • Generics and Collections
  • Inner Classes
  • Threads
  • The java.lang and java.util Packages

Otros apuntes: Es recomendable rendir el examen en inglés para evitar problemas en la traducción. El examen según veo puede ser como sigue bien 210 minutos / 72 preguntas / 59% pass score o bien 180 minutos / 60 preguntas / 55% pass score.

Acá les dejo los libros con los que me preparé para rendir el SCJP con éxito ... Bueno mis estimados javeros hasta la próxima publicación y espero consigan la ansiada certificación. xD saludos..

Download

Download

jueves, 1 de abril de 2010

Existe web hosting para java?.. en la internet

Me encontraba realizando un trabajo en condición de freelance.. cuando surgió la interrogante.. existe web hosting para java? en la nube ... Buscando en la web y por referencias de algunos contactos me tope con dailyrazor.com ...

Pues me puse a averiguar cual era el servicio que brindaban y viendolo bien respondia a mis expectativas de colgar un aplicativo web con Struts,Spring, Ibatis,Quartz, JavaMail y Log4j...

Pues nos animamos en adquirir el plan  Developer Hosting - Java Hosting - Private Tomcat Plans; y para que el servidor web respondió lo suficientemente bien como para estar satisfechos con la compra.



Por qué nos animamos adquirir el servicio en dailyrazor.com

  • Private Tomcat 5.x/6.x, JDK 1.5/1.6, Java 5/6, J2EE, JSP/Servlets support
  • Struts, Spring, JSF, Hiberenate, All Tomcat Frameworks supported
  • Tomcat Manager, Tomcat Admin, JNDI, JDBC, JavaMail, Log4J, WAR File Deployment Supported
  • Start/Stop Tomcat via SSH or Web based Console
  • MySQL, PostgreSQL, MS SQL Server Database supported on all plans
  • Host multiple Java web applications, domains, and JSP/Servlets sites
  • PHP, Perl, Python, CGI languages supported!
  • Panel de Control bastante amigable

Parte del Panel de Control:



Para mayor información sobre el plan adquirido dailyrazor.com/java/private_tomcat

Espero les sea útil esta info... se despide su amigo edisonjc7... ahora saldré con unos amigos a disfrutar de los feriados por semana Santa.. Saludos xD