« Zpět

RichFaces, trabajando con tablas (1)

El manejo avanzado de tablas es uno de los elementos más importantes dentro de las aplicaciones web. Habitualmente vamos a encontrar problemas a la hora de manejar tablas cuando el número de datos a renderizar es muy grande, debido entre otras cosas a:

  • Tiempos de respuesta elevados: debidos a la renderización y a la recuperación de los datos de la base de datos.
  • Problemas de memoria: almacenamiento de todos los registros recuperados de la base de datos.

RichFaces mejora el comportamiento de la tabla básica de la biblioteca HTML de JavaServer Faces trabajando con nuevos componentes. En este primer artículo, se pasan a describir las funcionalidades básicas que ofrecen estos componentes y cómo pueden ayudarnos a mejorar mejorar la gestión de tabla que trabajan con muchos datos.

Introducción

El problema de la gestión de tablas se describe en el siguiente esquema:

La renderización de tablas que muestran gran cantidad de datos acarrea varios problemas:

  1. Acceso a la base de datos.
  2. Almacenamiento de los registros como objetos Java en memoria.
  3. Renderización de todos los registros en la página que verá el usuario en el navegador.

La biblioteca de componentes JavaServer Faces de JBoss llamada RichFaces proporciona varios componentes para el manejo de tablas avanzado, proporcionando paginación, ordenación y filtrado de datos. Estos mecanismos intentan reducir los problemas de renderización provocados por la visualización de demasiados elementos en una tabla simultaneamente, este concepto ha sido identificado mediante el punto 3.

Los componentes RichFaces que vamos a utilizar son:

  • <rich:dataTable>
  • <rich:column>
  • <rich:dataScroller>

Estos componentes nos permitirán gestionar grandes cantidades de información de forma eficiente:

Creando tablas

Introducción

El componente rich:dataTable permite crear tablas en RichFaces. Este componente es muy parecido al componente con dos variaciones:

  • Skinnability: se aplican estilos sobre las tablas de una forma cómoda y sencilla.
  • Soporte Ajax: este componente es capaz de manejar y generar peticiones y respuestas Ajax.
  • También existen atributos para la gestión de eventos.
<rich:dataTable ...>
    ...
</rich:dataTable>

 

Los atributos más importantes del componente son:

  • value: la colección de datos que se va a mostrar. Se hace referencia a ésta mediante lenguaje de expresión.
  • var: nombre de la variable sobre la que se itera.
<rich:dataTable value="#{bean1.datos}" var="factura" ...>
    ...
</rich:dataTable>

Importante: se supone que el lector maneja JavaServer Faces, por esa razón, debe estar familiarizado con estos atributos, el lenguaje de expresión, etc.

El componente rich:column

La definición correcta de la tabla se hace habitualmente mediante el uso de otro componente llamado column. Como su nombre indica, permite crear columnas dentro de la tabla. La información que muestra cada columna se incluye dentro de ella, anidando otro componente. Por ejemplo, si se quiere mostrar un texto se anidará un componente

<rich:dataTable ...>   
   <rich:column>
      <h:outputText ...></h:outputText>   
   </rich:column>
   ...
</rich:dataTable>

Las facetas de la tabla

La definición de título, cabecera y pie de tabla se realiza mediante facetas: header, footer y caption. Como se puede ver en el ejemplo anterior, se definen cabeceras para cada columna:

<rich:dataTable ...>   
  <f:facet name="header">
    ...
  </facet>
  ...
</rich:dataTable>

Ejemplo

Se pasa a renderizar una tabla de facturas. Éstas se encuentran almacenadas en una lista definida en un mbean de JavaServer Faces (debe estar declarado en el fichero de configuración de JSF).

...
public class MBean1 {
 ...
 // Lista de facturas que muestra la tabla
 public List facturas;
  ...
}

La clase Factura tiene atributos para cada información que se quiere manejar de la factura:

...
public class Documento{

  private String concepto;
  private String codigo;
  private double importe;
  ...
}

La tabla en la vista se construye de la siguiente forma:

...
<rich:dataTable value="#{mbean1.facturas}" var="f" ...>
      <rich:column>
            <f:facet name="header">
               <h:outputText value="Concepto" />
            </f:facet>
            <h:outputText value="#{f.concepto}" />
       </rich:column>
       <rich:column>
             <f:facet name="header">
                <h:outputText value="Código de la factura" />
             </f:facet>
             <h:outputText value="#{f.codigo}" />
       </rich:column>
       <rich:column>
             <f:facet name="header">
                <h:outputText value="Importe" />
             </f:facet>
             <h:outputText value="#{f.importe}" />
       </rich:column>
 </rich:dataTable>
...

Paginando tablas

El proceso de paginación se lleva a cabo mediante el componente . Para realizar la paginación se utilizan peticiones Ajax. Este componente debe incluirse dentro del pie de la tabla padre o relacionarla mediante su atributo for:

- Dentro del pie:

<rich:dataTable ...>
  <rich:column>
    ...
  </rich:column>
  ...
  <f:facet name="footer">
    <rich:datascroller id="ds"></rich:datascroller>
  </f:facet>
</rich:dataTable>

- Mediante el atributo for: almacena el id de la tabla sobre la que se está actuando.

<rich:dataTable id="tablaEjemplo" ...>
  <rich:column>
    ...
  </rich:column>
  ...
</rich:dataTable>
<rich:datascroller id="ds" for="tablaEjemplo" ...></rich:datascroller>

En ambos casos se consigue algo de este estilo:

El componente dataScroller genera una barra numerada que permite recorrer todos los elementos de la tabla.

Ordenando y filtrando tablas

La ordenación de tablas se realiza trabajando con el atributo sortBy asociado a los componentes . Se muestra a continuación:

<rich:dataTable value="#{mbean1.facturas}" var="f" ...>
  <rich:column sortBy="#{f.concepto}">
            <f:facet name="header">
               <h:outputText value="Concepto" />
            </f:facet>
            <h:outputText value="#{f.concepto}" />
   </rich:column>
   <rich:column>
             <f:facet name="header">
                <h:outputText value="Código de la factura" />
             </f:facet>
             <h:outputText value="#{f.codigo}" />
   </rich:column>
   <rich:column>
             <f:facet name="header">
                <h:outputText value="Importe" />
             </f:facet>
             <h:outputText value="#{f.importe}" />
   </rich:column>  ...
</rich:dataTable>

El proceso de filtrado se lleva a cabo aplicando sobre las columnas, es decir, los componentes el atributo filterBy.

<rich:dataTable value="#{mbean1.facturas}" var="f" ...>
  <rich:column sortBy="#{f.concepto}" filterBy="#{f.concepto}">
            <f:facet name="header">
               <h:outputText value="Concepto" />
            </f:facet>
            <h:outputText value="#{f.concepto}" />
   </rich:column>
   <rich:column>
             <f:facet name="header">
                <h:outputText value="Código de la factura" />
             </f:facet>
             <h:outputText value="#{f.codigo}" />
   </rich:column>
   <rich:column>
             <f:facet name="header">
                <h:outputText value="Importe" />
             </f:facet>
             <h:outputText value="#{f.importe}" />
   </rich:column>  ...
</rich:dataTable>
...

Si se aplican ambos conceptos sobre la misma tabla, se obtiene algo así:

Conclusiones

Los componentes para el manejo de tablas de RichFaces, utilizados de forma estándar, nos permiten mejorar las prestaciones de nuestras tablas en cuanto al número de elementos renderizados en nuestras páginas simultáneamente, pero en ningún caso, nos permite reducir el número de objetos almacenados en memoria ni el tipo de consultas que realizo sobre la base de datos. En próximos artítulos se describe este proceso de mejora.

Actualización

Si quieres seguir aprendiendo sobre este tema puedes acceder al post "RichFaces, trabajando con tablas (2)".

 

Komentáře
Trackback URL:

comments powered by Disqus