Manual JasperReports

55
UNIVERSIDAD DE EL SALVADOR ADACAD JasperReports Elaborado por: Rudy Chicas Jefe de ADACAD Ciudad Universitaria, diciembre de 2010

Transcript of Manual JasperReports

UNIVERSIDAD DE EL SALVADOR

ADACAD

JasperReports

Elaborado por:

Rudy Chicas

Jefe de ADACAD

Ciudad Universitaria, diciembre de 2010

Indice de contenido

INTRODUCCION..........................................................................................................................i

INSTALACION DE PLUGIN iReport PARA NetBeans................................................................1

ORIGENES DE DATOS..............................................................................................................1

Conexiones JDBC...................................................................................................................3

JavaBeans..............................................................................................................................8

ESTRUCTURA DE REPORTES...............................................................................................15

ELEMENTOS INTERNOS DE UN REPORTE..........................................................................16

Styles....................................................................................................................................17

Parameters...........................................................................................................................17

Fields.....................................................................................................................................19

Variables...............................................................................................................................19

Scriplets................................................................................................................................20

Bandas..................................................................................................................................21

DISEÑO DE REPORTES..........................................................................................................21

Elementos de reportes..........................................................................................................21

Construyendo el reporte.......................................................................................................23

Manejo de Grupo..................................................................................................................35

IMPLEMENTACION DE REPORTES EN APLICACION JSF...................................................45

Configuración de los servlets................................................................................................45

Clases para el soporte de reportes......................................................................................47

Clase de implementación de Reporte..................................................................................50

Integrando con la vista..........................................................................................................51

BIBLIOGRAFIA.........................................................................................................................53

INTRODUCCION

iReport es la interfaz de usuario más frecuentemente utilizada para el uso de las librerías JasperReports. JasperReports es una herramienta para la creación de informes en Java, que permite la adición de contenido enriquecido a los informes.

iReport permite crear los archivos fuentes de los reportes, y compilarlos para crear un archivo de extensión .jasper. Estos archivos son los que se utilizan para la implementación de los reportes en las aplicaciones Java.

i

INSTALACION DE PLUGIN iReport PARA NetBeans

El plugin de iReport para NetBeans puede ser descargado en la siguiente dirección:

http://plugins.netbeans.org/PluginPortal/faces/PluginDetailPage.jsp?pluginid=4425

Para realizar la instalación hay que seguir la forma típica para instalar un plugin en NetBeans.

ORIGENES DE DATOS

Tanto el IDE tradicional de iReport como el plugin de iReport para NetBeans permiten la configuración de varios orígenes de datos.

Los orígenes de datos que pueden ser usados con reportes JasperReports son:

• Conexiones JDBC

• JavaBeans

• XML

• CSV

• Hibernate connection

• Spring-loaded Hibernate connection

• Proveedor de origen de datos JasperReports

• Orígenes de datos personalizados

• Conexión LDAP Mondrian

• Conexión XML/A

• EJBQL Connection

• Origen de datos vacío

En este documento nos centraremos en el estudio de las conexiones JDBC y los orígenes de datos JavaBeans.

Los orígenes de datos sirven para tener acceso a un conjunto de datos en tiempo de diseño de los reportes, y no significa que al ser configurado para el diseño del reporte, estará disponible en tiempo de ejecución.

Para definir un origen de datos es necesario hacer clic sobre el botón de configuración. La siguiente figura muestra el botón de configuración de orígenes de datos en una instalación en NetBeans.

1

2

Conexiones JDBC

Los orígenes de datos del tipo JDBC son conexiones directas a la base de datos que estarán disponibles en tiempo de diseño.

Para definir una conexión JDBC se debe acceder al editor de orígenes de datos de iReport, y seleccionar la opción Database JDBC connection.

Al hacer clic en el botón Next aparecerá la interfaz de configuración de la conexión.

3

En este interfaz habrá que especificar el nombre de la conexión, el driver JDBC a utilizar, el URL de la conexión, el nombre de usuario de la base con la que nos queremos conectar y el password.

4

Para probar la conexión, podemos usar el botón Test. Se nos pedirá que confirmemos la clave del usuario, y si no hay errores, el sistema nos enviará un mensaje de éxito de la conexión. Posteriormente podemos guardar los datos de la conexión.

5

Para especificar qué datos se usarán en el reporte, es necesario especificar una consulta para el reporte (Report Query). La consulta del reporte puede ser de cualquiera de los tipos de orígenes de datos soportados.

Para las conexiones JDBC la consulta del reporte es una consulta SQL a la base de datos, como se muestra en la siguiente figura.

6

Al escribir la consulta, iReport retorna los campos especificados en la sentencia SQL y sus tipos de datos. Es también posible hacer una revisión de los datos en la base de datos haciendo clic en el botón Refresh Preview Data.

7

JavaBeans

Los orígenes de datos del tipo JavaBeans set Datasource son orígenes de datos basados en clases Java que retornarán una colección (Collection) o arreglo (Array) de objetos de una clase Java que contiene los datos que necesitamos mostrar en el reporte.

Aunque no es indispensable, si deseamos contar con un conjunto de datos que nos sirva para realizar pruebas del reporte en tiempo de diseño, deberemos especificar una clase que genere dichos datos. Esta clase no será parte de nuestra aplicación, por lo que debemos escribirla en un paquete separado del resto.

Como ejemplo, se muestra la clase CarrerasDataSourceDesing, que se encuentra en el paquete reportdesing.

8

Lista de código 3.2.1: Clase CarrerasDataSourceDesing, origen de datos para el diseño del reporte.

/* * To change this template, choose Tools | Templates * and open the template in the editor. */

package reportdesing;

import control.CarrerasBean;import java.util.ArrayList;import java.util.Collection;

/** * * @author rchicas */public class CarrerasDataSourceDesing { public static Collection getCarreras(){ ArrayList carreras = new ArrayList();

for(int i=0;i<=10;i++){ CarrerasBean carrera = new CarrerasBean();

carrera.setCodigo("ABC" + i); carrera.setIdCarrera(i); carrera.setMaxInscribir(5); carrera.setNombre("Nombre Carrera" + i); carrera.setPlanEstudios("Plan"+i); carrera.setTotalUV(48+i);

carreras.add(carrera); }

return carreras; }}

Adicionalmente es necesario especificar el método estático que devolverá la colección o el arreglo de objetos, que en este caso es llamado getCarreras.

9

Para acceder a la clase y su método, iReport requiere de la configuración de Classpath, en el que se debe especificar la ruta donde se encuentra las clases a las que se está haciendo referencia. Si utilizamos el plugin de NetBeans, para configurar el Classpath es necesario ir al menú Opciones (Options), seleccionar iReport y la pestaña Classpath.

10

Si iReport puede acceder a la clase y su método, al presionar el botón Test mostrará un mensaje de éxito.

Para utilizar este tipo de orígenes de datos, se debe especificar la clase de los objetos que nos devolverá el método especificado, en este caso getCarreras. En otras palabras, el método getCarreras devuelve una colección de objetos del tipo CarrerasBean, por lo que la clase que se especifique en la consulta del reporte debe ser del tipo CarrerasBean.

11

En la interfaz en la que se especifica la consulta del reporte, se debe seleccionar los atributos de la clase que formarán parte de nuestro reporte. Esto se hace seleccionando los atributos de la clase y haciendo clic en el botón Add selected field. Estos serán los campos que estarán disponibles en el reporte como campos (fields).

12

Si deseamos ver los datos de prueba hacemos clic en el botón Refresh Preview Data, lo que ejecutará el método getCarreras y devolverá la colección de objetos.

13

Puede observarse que los datos que devuelve la vista previa son los datos que se generan en el método getCarreras, no los que se encuentran en la base de datos, puesto que no se está usando una conexión a la base.

La configuración de la clase que generará la colección de datos es opcional, ya que su único objetivo es poner a nuestra disposición un conjunto de datos para la vista preliminar del reporte.

14

En caso de optar por no crear dicha clase, las pruebas del reporte deberán hacerse cuando éste haya sido integrado a la aplicación.

ESTRUCTURA DE REPORTES

Un reporte basado en JasperReports consta de los siguiente elementos:

• Title: Titulo del reporte. La información contenida en esta banda será mostrada una sola vez en la primera página del reporte.

• Page Header: Encabezado de página. La información contenido en esta banda será mostrada en cada página del reporte.

• Column Header: Encabezado de columna. El uso más frecuente de esta banda es para desplegar los encabezados de las tablas de datos en los reportes tipo cuadrículas.

• Detail: Detalle del reporte. En esta banda incluyen los campos que constituyen el detalle del reporte. En un reporte tipo cuadrícula se colocan los campos de la tabla.

• Column Footer: Pie de columna. Se utiliza generalmente para totalizar el detalle de cada campo (columna). Tanto el encabezado de columna, como el pié de columna solo serán mostrados cuando inicia el set de datos y cuando termina.

Si se requiere que el encabezado de las columnas aparezca en todas las páginas, se deberán colocar los encabezados en el elemento Page Header.

• Page Footer: Será mostrado en todas las páginas del reporte.

• Sumary: Resumen. Se muestra únicamente en la última página del reporte. Generalmente es usado para consolidar datos mostrados en las otras partes del reporte.

15

ELEMENTOS INTERNOS DE UN REPORTE

La estructura de objetos para un reporte Jarper puede verse en la barra de objetos del reporte mostrado en la siguiente figura.

16

Utilizaremos la estructura de objetos del árbol de objetos, para explicar las características básicas de cada elemento.

Styles

El nodo Styles permite agregar estilos personalizados o referencias a estilos por defecto al reporte. Un estilo es una colección de propiedades predefinidas que se refieren al aspecto de los elementos (como color de fondo, bordes, y fuentes).

Es posible definir un estilo por defecto para el reporte, para que todas las propiedades no definidas de un elemento se refieran e ese estilo.

Parameters

Los parámetros definidos por defecto son utilizados para recibir información de la clase que invoca y ejecuta el reporte. Pueden ser utilizados para guiar un comportamiento específico durante el tiempo de ejecución y para proveer datos adicionales para el contexto de impresión como imágenes, títulos, etc.

17

La referencia a los parámetros se realizar a través de la expresión:

$P{nombre_parametro}

El parámetro especial REPORT_PARAMETERS_MAP es de tipo Map compuesto por el par de valores <Nombre_Parametro, Valor>. La expresión empleada para invocar un valor de ese parámetro tendrá la forma:

$P{REPORT_PARAMETERS_MAP}.get(“Nombre_Parametro”)

18

Fields

Los campos se refieren a los campos del conjunto de datos que devuelve un origen de datos. Estos son identificados por un nombre, un tipo y una descripción opcional.

La forma de hacer referencia a un campo es a través de la expresión:

$F{nombre_campo}

Variables

Las variables son objetos que se usan para almacenar resultados de cálculos como subtotales, sumas, entre otros. Las variables deben tener un tipo de dato asignado, tal como los parámetros y los campos.

Las variables cuentan con algunos atributos que las diferencian de los parámetros y los campos:

19

• Calculation: Es el método de cálculo que se aplicará a la variable. Los tipos de cálculos que se pueden seleccionar son:

◦ Nothing. No se realiza ningún cálculo.

◦ Count. Cuenta el número de veces que la expresión resulta en valores diferentes a nulo.

◦ Distict count. Cuenta el número expresiones resultantes diferentes entre sí. El orden entre las expresiones no es tomado en cuenta.

◦ Sum. Para cada iretación, suma al valora actual el valor de la expresión actual.

◦ Average. Calcula el promedio aritmético de todas las expresiones recibidas.

◦ Lowest. Retorna la expresión de menor valor de las recibidas.

◦ Highest. Retorna la expresión de mayor valor de las recibidas.

◦ Standard derivation. Calcula la desviación estándar de las expresiones recibidas.

◦ Variance. Calcula la varianza de las expresiones recibidas.

◦ System. Esta opción no realiza ningún cálculo, ni se evalúa ninguna expresión. El reporteador mantiene en memoria el último valor asignado a la variable.

◦ First. Devuelve la primera expresión evaluada.

• Las variables también cuentan con un tipo de reinicio (reset type), que especifica el momento en que una variable será reiniciada. Los tipos de reinicio son:

◦ None. El valor inicial de la variable es ignorado siempre.

◦ Report. La variable será inicializada solo cuando se inicia la creación del reporte.

◦ Page. La variable es inicializada cada vez que se despliega una página.

◦ Column. La variable es inicializada cada vez que se despliega una columna.

◦ Group. La variable es inicializada cada vez que se despliega un grupo nuevo.

Scriplets

Para implementar un scriptlet es necesario extender la clase nt.sf.jasperreports.engine.JRAbstractScriptlet. Esta clase expone un conjunto de métodos para manejar los eventos que ocurren durante la generación de un reporte, y provee la estructura de datos para acceder a todas las variables, campos y parámetros del reporte.

En otras palabras, un scriptlet permite manipular un reporte desde una clase Java, de tal manera que es posible modificar el comportamiento especificado durante su diseño.

20

Bandas

Como se explicó en el apartado Estructura de reportes la estructura de un reportes está compuesta por 8 bandas principales y el backgroud (9 bandas en total). Pueden agregarse dos bandas más: group header y group footer.

DISEÑO DE REPORTES

El diseño de los reportes se realiza a través de la paleta de elementos de reportes. Los elementos son insertados en la banda en la que deseamos que aparezca, arrastrando el elemento de la paleta a la banda correspondiente.

Elementos de reportes

• Line

• Rectangle

• Elipse

• Static Text

• Text Field

• Image

• Subreport

• Cosstab

• Chart

• Frame

Los elementos del reporte están disponibles en la paleta de controles de iReport en NetBeans (barra de herramientas en la interfaz clásica de iReport).

21

Para agregar un elemento al reporte, se debe seleccionar uno de los controles y arrastrarlo a la banda en la que desea que aparezca.

22

Una vez que el elemento se encuentra en la banda, puede ser editado a través de la ventana propiedades.

Construyendo el reporte

Para explicar el proceso de construcción de reportes se realizará como ejemplo, un reporte que muestre las carreras almacenadas en la tabla carreras de la base de datos.

Dado que en las aplicaciones instituciones se usará JavaBean datasource como orígenes de datos, desarrollaremos este ejemplo usando ese tipo de origen de datos.

Lo primero será configurar el origen de datos como se explicó en el apartado Orígenes de datos/JavaBeans. Cuando ya tenemos la consulta del reporte configurada, podemos proceder al diseño del reporte.

La clase CarrerasBean que será el JavaBean a utilizar como origen de datos se muestra en la lista de código 6.2.1.

Lo primero que haremos es insertar un texto estático con el título del reporte. Para ello hay que arrastrar a la banda Title un elemento Static Text de la paleta de controles. Los elementos de texto estático pueden ser editados al hacer doble clic sobre él.

23

Lista de código 6.2.1: Bean administrado CarrerasBean

package control;

import dao.impl.CarreraDaoImpl;import javax.faces.context.FacesContext;import javax.servlet.ServletContext;import org.springframework.web.context.support.WebApplicationContextUtils;

/* * * @author rchicas */public class CarrerasBean {

private int idCarrera; private String codigo; private String nombre; private String planEstudios; private int totalUV; private int maxInscribir;

/** * Acción para almacenamiento */ public void guardarAction() { ServletContext servletContext = (ServletContext) FacesContext.getCurrentInstance().getExternalContext().getContext(); CarreraDaoImpl carreraDao = (CarreraDaoImpl) WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext).getBean("carreraDao");

Integer id = carreraDao.guardar(this); }

public void actualizarAction() { ServletContext servletContext = (ServletContext) FacesContext.getCurrentInstance().getExternalContext().getContext(); CarreraDaoImpl carreraDao = (CarreraDaoImpl) WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext).getBean("carreraDao");

carreraDao.actualizar(this); }

public void borrarAction() { ServletContext servletContext = (ServletContext) FacesContext.getCurrentInstance().getExternalContext().getContext(); CarreraDaoImpl carreraDao = (CarreraDaoImpl) WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext).getBean("carreraDao");

carreraDao.borrar(idCarrera); }

.../*Métodos get y set */...}

24

Una vez que se ha habilitado la posibilidad de edición del texto por defecto, escribimos

Universidad de El SalvadorSistema de Administración Académica

Otra posibilidad para editar el texto de un elemento de texto estático es ir a las propiedades del elemento y hacer clic en el botón de modificación de la propiedad Text.

Ahora podemos aplicar formato al texto. En este caso, haremos que el texto sea mostrado en negritas. Para ello, en la ventana de propiedades del elemento, buscar la opción Bold y hacer clic en el checkbox que corresponde.

25

Ahora agregaremos el título del reporte, que obtendremos de un parámetro enviado al reporte desde la aplicación que lo invocará.

Para ello, incorporamos a la banda Title un elemento del tipo Text Field, que inicialmente aparecerá vacío.

Una vez que se ha agregado a la banda, hacemos clic derecho en él y seleccionamos la opción Edit expression.

26

En la ventana de edición de expresiones, escribimos la expresión:

$P{REPORT_PARAMETERS_MAP}.get(“ReportTitle”)

Esta expresión evalúa el mapa de parámetros REPORT_PARAMETERS_MAP y obtiene el parámetro ReportTitle.

Ahora pasaremos a incorporar los campos de los datos que deseamos mostrar. Para ello, podemos seleccionar los campos que se han definido como parte de la consulta del reporte.

En el árbol de objetos del reporte, expandimos el nodo Fields. Esto nos mostrará los campos disponibles que fueron configurados en la consulta del reporte. Una forma de crear el cuadro de datos que deseamos mostrar es seleccionar los campos y arrastrarlos a la banda Detail. iReport colocará etiquetas en la banda Column Header y los elementos Text Field en la banda Detail.

27

Modificamos los Static Text de Column Header, escribiéndo el texto en mayúsculas, modificando la propiedad Bold para que el texto sea mostrado en negritas y la propiedad Horizontal Alignment a Center para que el texto sea centrado.

Dado que se trata de una tabla de datos, agregaremos los bordes a la tabla. Para ello, en el encabezado del reporte, agregamos un elemento Rectangle para que sea el marco de los encabezados de columna.

28

Para que el elemento sea mostrado, hacer clic derecho en el rectángulo y seleccionamos la opción Send to Back, para que el elemento quede detrás de los cuadros de texto estático.

Posterior a eso, es necesario agregar las líneas de los campos. Para ello usaremos objetos Line, haciendo una especie de rectángulo abierto por arriba. En otras palabras, habrá que agregar una línea horizontal inferior, y las líneas verticales de separación entre los campos. La línea horizontal superior no es necesaria.

Una vez hecho esto, incorporaremos al reporte los campos que muestren el número de página y el total de páginas. iReport ya cuenta con una herramienta que ingresa los elementos de texto para los campos y sus respectivos valores.

Para hacer esto, es necesario arrastrar de la paleta de controles, la herramienta Page X of Y a la banda de Encabezado de página.

29

La herramienta agrega a la banda dos elementos uno con el valor:

"Pág. "+$V{PAGE_NUMBER}+" de"

Y el otro con el valor:

" " + $V{PAGE_NUMBER}

En ambos casos, el tipo de dato del elemento es de tipo String, por lo que es permitido realizar la concatenación de los valores. El tipo de dato de las variables, campos, parámetros y de los Text Fields son definidos en la propiedad Expression class.

Se puede observar que el funcionamiento del control de páginas está basado en una variable de nombre PAGE_NUMBER, que es una variable predefinida en todos los reportes creados con iReport.

30

31

Por ser una variable intrínseca sus propiedades no están disponibles en tiempo de diseño. Sin embargo es importante tener claro que se trata de una variable de tipo entera y cuya operación es COUNT y cuyo tipo de reinicio es Report.

Estas características harán que la variable cuente el número de veces que es evaluada (invocada) en el reporte, acumulando 1 por cada vez que es evaluada. Esto permite que al utilizar la variable en el reporte, en el primer cuadro de texto (que muestra la página actual) se utiliza el tipo de evaluación Now, es decir que el valor de la variable se mostrará en ese cuadro de texto cada vez que sea necesario desplegar ese elemento.

En el siguiente cuadro de texto, que muestra el total de páginas, la variable se evalúa en el contexto del reporte. En otras palabras, cuando ese cuadro de texto sea evaluado, el cuadro de texto mostrará el valor con el que terminó esa variable al finalizar la construcción del reporte. Eso significa, el total de páginas.

Finalmente, ingresamos al reporte un logotipo de la institución. Para ello arrastramos un control Image de la paleta de controles.

Esto nos mostrará un elemento de imagen dentro de la banda a la que la hayamos arrastrado. Para este caso, la arrastraremos a la banda Title

32

Ajustamos la imagen para que se muestre con el tamaño y ubicación que sea necesaria.

33

Para verificar el diseño del reporte, podemos usar la opción Preview. Para ello hacemos clic en la pestaña Preview, compilará el reporte y generará una vista preliminar del mismo.

Podemos observar que el título del reporte se muestra con un valor null. Esto es así porque el valor que se desplegará es un parámetro que no ha sido recibido. Para que el reporte no muestre la palabra null cuando se encuentran valores nulos, es necesario modificar la propiedad del elemento a Blank when null.

34

Manejo de grupos

Los grupos es la forma en la que JasperReports permite organizar los datos en bloques de datos de acuerdo a los criterios de agrupamiento. Un grupo es definido a través de una expresión. Cuando esta expresión cambia su valor, un nuevo grupo es iniciado.

Para ejemplificar esto, usaremos el ejemplo anterior, agregando el atributo facultad a la clase CarrerasBean y por ende, agregando al método que genera los datos de muestra para tiempo de diseño, el código necesario para que incluya valores para ese atributo.

La clase CarrerasBean modificada se muestra en la lista de código 6.3.1

Lista de código 6.3.1: Bean administrado CarrerasBean modificado

package control;

import dao.impl.CarreraDaoImpl;import javax.faces.context.FacesContext;import javax.servlet.ServletContext;import org.springframework.web.context.support.WebApplicationContextUtils;

/* * To change this template, choose Tools | Templates * and open the template in the editor. *//** * * @author rchicas */public class CarrerasBean {

private int idCarrera; private String codigo; private String nombre; private String planEstudios; private int totalUV; private int maxInscribir; private String facultad;

...

/** * @return the facultad */ public String getFacultad() { return facultad; }

/** * @param facultad the facultad to set */ public void setFacultad(String facultad) { this.facultad = facultad; }}

35

El método getCarreras de la clase CarrerasDataSourceDesing se muestra en la lista de código 6.3.2.

Lista de código 6.3.2: Clase CarrerasDataSourceDesing modificada.

package reportdesing;

import control.CarrerasBean;import java.util.ArrayList;import java.util.Collection;

/** * * @author rchicas */public class CarrerasDataSourceDesing { public static Collection getCarreras(){ ArrayList carreras = new ArrayList();

for(int i=0;i<=10;i++){ CarrerasBean carrera = new CarrerasBean();

carrera.setCodigo("ABC" + i); carrera.setIdCarrera(i); carrera.setMaxInscribir(5); carrera.setNombre("Nombre Carrera" + i); carrera.setPlanEstudios("Plan"+i); carrera.setTotalUV(48+i);

if(i%2 > 0 || i==0) carrera.setFacultad("Facultad"+i); else carrera.setFacultad("Facultad"+(i-1));

carreras.add(carrera); }

return carreras; }}

El método genera una carrera para la facultad 0 y dos carreras para el resto de las facultades, para permitirnos apreciar el manejo de los grupos.

Posterior a ello, habrá que agregar el atributo faculta a la consulta del reporte. Una vez hecho esto, es necesario agregar el grupo al reporte, para ello hay que hacer clic derecho en el nodo principal del árbol de objetos del reporte o sobre una de las bandas. Esto nos mostrará un menú contextual en el que deberemos seleccionar la opción Add Report Group.

36

Esto nos mostrará un asistente con el que podremos configurar el grupo. Indicamos que nombre del grupo y la expresión que lo definirá. En nuestro caso, la expresión es el campo facultad.

37

Cuando finalizamos la configuración del grupo, iReport nos muestra las bandas que hemos incluido en el reporte. En este caso las bandas Group Header y Group Footer.

38

Agregamos un texto de campo a la banda facultad Group Header para que cada vez que cada vez que inicie un nuevo grupo, muestre el nombre del nuevo grupo. En este caso, los grupos están basados en el nombre de la facultad, por lo que el campo a mostrar es el de facultad.

39

40

Copiamos los elementos de línea para la rejilla de datos y la pegamos en la banda que estamos editando.

41

42

iReport crea una variable contador por cada grupo. Esto permite contar el número de registros por cada grupo.

Usaremos esa variable para que en el footer del grupo nos muestre el valor con un texto.

Para ello, agregamos un Text Field a la banda facultad Group Footer, y editamos la expresión.

Ahora copiamos los elementos de línea de la banda facultad Group Header y la pegamos en la banda que estamos editando.

Para ajustar el tamaño de las bandas, hay que mover el borde inferior de la banda hacia arriba o abajo según se desee. Para ajustar la banda a su límite inferior, basta con dar doble clic al borde inferior y se ajustará a la posición del elemento más inferior de la banda.

43

44

Las modificaciones realizadas para los grupos han sido hechas únicamente para que estén disponibles en tiempo de diseño, ya que en la base de datos no existe ese campo. Por esta razón, a la hora de realizar la implementación, no se incluirán las modificaciones relacionadas a esta sección.

IMPLEMENTACION DE REPORTES EN APLICACION JSF

Configuración de los servlets

En las aplicaciones JSP, los reportes son resueltos como parte del servlet principal de la aplicación. JSF nos permite configurar varios servlets en una aplicación. Las librerías de JasperReports nos permiten configurar estos servlets independientes entre sí, de acuerdo a los formatos de documento que deseemos que soporte nuestra aplicación.

Lista de código 7.1.1: Servlets correspondientes a los formatos soportados

<!-- JasperReports Servlet --> <servlet> <servlet-name>PdfServlet</servlet-name> <servlet-class>net.sf.jasperreports.j2ee.servlets.PdfServlet</servlet-class> </servlet> <servlet> <servlet-name>JExcelApiServlet</servlet-name> <servlet-class>net.sf.jasperreports.j2ee.servlets.JExcelApiServlet</servlet-class> </servlet> <servlet> <servlet-name>RtfServlet</servlet-name> <servlet-class>net.sf.jasperreports.j2ee.servlets.RtfServlet</servlet-class> </servlet>

<!-- JasperReports Servlet Mapping --> <servlet-mapping> <servlet-name>PdfServlet</servlet-name> <url-pattern>/servlets/report/PDF</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>JExcelApiServlet</servlet-name> <url-pattern>/servlets/report/EXCEL</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>RtfServlet</servlet-name> <url-pattern>/servlets/report/RTF</url-pattern> </servlet-mapping>

También crearemos dos clases que darán soporte a los reportes. La primera de ellas ReportUtil servirá para implementar los métodos de llenado y exportado de los archivos de JasperReports compilados (.jasper).

45

Clases para el soporte de reportes

Lista de código 7.2.1: Clase de soporte a los reportes

package util;

import java.io.File;import java.io.PrintWriter;import java.util.Map;

import javax.servlet.ServletContext;

import net.sf.jasperreports.engine.JRAbstractExporter;import net.sf.jasperreports.engine.JRDataSource;import net.sf.jasperreports.engine.JRException;import net.sf.jasperreports.engine.JRExporterParameter;import net.sf.jasperreports.engine.JasperFillManager;import net.sf.jasperreports.engine.JasperPrint;import net.sf.jasperreports.engine.export.JRHtmlExporter;import net.sf.jasperreports.engine.export.JRHtmlExporterParameter;

public class ReportUtil {

public static JasperPrint fillReport(File reportFile, Map<String, Object> parameters, JRDataSource jrDataSource) throws JRException { parameters.put("BaseDir", reportFile.getParentFile());

JasperPrint jasperPrint = JasperFillManager.fillReport(reportFile.getPath(), parameters, jrDataSource);

return jasperPrint; }

public static String getJasperFilePath(ServletContext context, String reportDir, String jasperFile) { return context.getRealPath(reportDir + jasperFile); }

private static void exportReport(JRAbstractExporter exporter, JasperPrint jasperPrint, PrintWriter out) throws JRException { exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint); exporter.setParameter(JRExporterParameter.OUTPUT_WRITER, out);

exporter.exportReport(); }

public static void exportReportAsHtml(JasperPrint jasperPrint, PrintWriter out) throws JRException { JRHtmlExporter exporter = new JRHtmlExporter(); exporter.setParameter(JRHtmlExporterParameter.IS_USING_IMAGES_TO_ALIGN, Boolean.FALSE); exporter.setParameter(JRHtmlExporterParameter.IS_REMOVE_EMPTY_SPACE_BETWEEN_ROWS, Boolean.TRUE); exporter.setParameter(JRHtmlExporterParameter.CHARACTER_ENCODING, "ISO-8859-9");

exportReport(exporter, jasperPrint, out); }}

46

La clase AbstractBaseReportBean es una clase abstracta que implementa los métodos básicos para el manejo de los reportes. La clase que implementen esta clase, tendrán a su disposición los métodos elementales para el manejo de los reportes, lógicamente debiendo implementar aquellos que no están implementados.

Lista de código 7.2.2: Clase abstracta que implementa las funciones básica del manejo de reportes.

package util;

import java.io.File;import java.io.IOException;import java.util.HashMap;import java.util.Map;

import javax.faces.context.ExternalContext;import javax.faces.context.FacesContext;import javax.servlet.ServletContext;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;

import net.sf.jasperreports.engine.JRDataSource;import net.sf.jasperreports.engine.JRException;import net.sf.jasperreports.engine.JasperPrint;import net.sf.jasperreports.j2ee.servlets.BaseHttpServlet;

public abstract class AbstractBaseReportBean {

public enum ExportOption {

PDF, HTML, EXCEL, RTF } private ExportOption exportOption; private String reportDir = "/";

public AbstractBaseReportBean() { super(); setExportOption(ExportOption.PDF); }

protected void prepareReport() throws JRException, IOException { ExternalContext externalContext = FacesContext.getCurrentInstance().getExternalContext();

ServletContext context = (ServletContext) externalContext.getContext(); HttpServletRequest request = (HttpServletRequest) externalContext.getRequest(); HttpServletResponse response = (HttpServletResponse) externalContext.getResponse();

File reportFile = new File(ReportUtil.getJasperFilePath(context, getReportDir(), getNombArch() + ".jasper"));

JasperPrint jasperPrint = ReportUtil.fillReport(reportFile, getReportParameters(), getJRDataSource());

47

if (getExportOption().equals(ExportOption.HTML)) { ReportUtil.exportReportAsHtml(jasperPrint, response.getWriter()); } else { request.getSession().setAttribute(BaseHttpServlet.DEFAULT_JASPER_PRINT_SESSION_ATTRIBUTE, jasperPrint); response.sendRedirect(request.getContextPath() + "/servlets/report/" + getExportOption()); }

FacesContext.getCurrentInstance().responseComplete(); }

public ExportOption getExportOption() { return exportOption; }

public void setExportOption(ExportOption exportOption) { this.exportOption = exportOption; }

protected Map<String, Object> getReportParameters() { return new HashMap<String, Object>(); }

/** * @return the reportDir */ public String getReportDir() { return reportDir; }

/** * @param reportDir the reportDir to set */ public void setReportDir(String reportDir) { this.reportDir = reportDir; }

protected abstract JRDataSource getJRDataSource();

protected abstract String getNombArch();}

Un ejemplo de la implementación de la clase abstracta, es la lista de código 7.3.1.

48

Clase de implementación de Reporte

Lista de código 7.3.1: Clase de implementación del reporte para carreras.

package control;

import util.AbstractBaseReportBean;import java.util.HashMap;import java.util.Map;import javax.el.ValueExpression;import javax.faces.context.FacesContext;

import net.sf.jasperreports.engine.JRDataSource;import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource;

public class ReporteCarrerasBean extends AbstractBaseReportBean {

private final String NOMBRE_ARCHIVO = "carreras";

@Override protected String getNombArch() { return this.NOMBRE_ARCHIVO; }

@Override protected Map<String, Object> getReportParameters() { Map<String, Object> reportParameters = new HashMap<String, Object>();

reportParameters.put("ReportTitle", "Listado de carreras registradas en el sistema");

return reportParameters; }

@Override protected JRDataSource getJRDataSource() { ValueExpression ve = FacesContext.getCurrentInstance().getApplication().getExpressionFactory().createValueExpression(FacesContext.getCurrentInstance().getELContext(), "#{buscarCarreraBean}", BuscarCarreraBean.class);

BuscarCarreraBean buscarCarreraBean = (BuscarCarreraBean) ve.getValue(FacesContext.getCurrentInstance().getELContext());

JRBeanCollectionDataSource dataSource = null;

if(buscarCarreraBean !=null){ if(buscarCarreraBean.getListaCarreras() == null) buscarCarreraBean.buscarTodosAction(); dataSource = new JRBeanCollectionDataSource(buscarCarreraBean.getListaCarreras()); }

return dataSource; }

49

public String execute() { try { super.prepareReport(); } catch (Exception e) {

e.printStackTrace(); }

return null; }}

Integrando con la vista

La interfaz que se encargará de invocar al método execute de la clase que implementa el reporte específico (ReporteCarrerasBean), desplegará las opciones de los formatos disponibles para el reporte, y la llamada al método a través de una acción vinculada a un botón, como se muestra en la lista de código 7.4.1.

Lista de código 7.4.1: Código JSF que pone el reporte a disposición del usuario

<h:form id="form"> <h:selectOneRadio value="#{reporteCarrera.exportOption}"> <f:selectItem itemValue="PDF" itemLabel="PDF"/> <f:selectItem itemValue="HTML" itemLabel="HTML"/> <f:selectItem itemValue="EXCEL" itemLabel="EXCEL"/> <f:selectItem itemValue="RTF" itemLabel="RTF"/> </h:selectOneRadio> <h:commandButton action="#{reporteCarrera.execute}" value="Get Report" /> </h:form>

50

51

BIBLIOGRAFIA

• The Definitve Guide to iReport

Guilio Toffoli

Apress

• JasperReports and JSF Integration

http://www.jroller.com/hakan/entry/jasperreports_and_jsf_integration

• iReport Tutorials & Help

http://jasperforge.org/website/ireportwebsite/IR%20Website/ir_documentation.html?header=project&target=ireport

52