Contacto

Nos puedes enviar un artículo a publicar (si te fue útil, seguro que a otros también).
Nos puedes sugerir temas/profundidad de interés.
correo-e - perfil

Busquedas

Filtros en jsp y servlets

 Los filtros - filters - en una aplicación web, nos permiten interceptar el request antes de que éste llegue al servlet o jsp correspondiente, y también nos permite interceptar el response del servlet o jsp antes de que llegue al cliente.

  -------------------     request      -----------                   -----------------
 |    Cliente        |  ------------->  | FILTRO |   -------->  | Contenedor  |
 |    Navegador  | <-------------- |              | <--------   | jsp servlet    |
  ------------------      response    ------------                 -----------------

 Los filtros pueden estar encadenados. Para un request dado pueden ejecutarse más de un filtro. FILTRO_1 --> FILTRO_2 --> FILTRO_n --> CONTENEDOR

 Los filtros tienen que declararse en el Deployment Descriptor (el archivo web.xml). En este lugar se indica el/los filtros a ejecutar para un request, y el orden.

 La clase donde creamos el filtro tiene que implementar la interface Filter, e implementar tres métodos de esta interface, siendo "doFilter()" el que contiene  la lógica principal, y es llamado cada vez que se ejecuta el filtro.
 Dentro de este método, cuando se quiere ejecutar el siguiente filtro, se invoca a "doFilter" del objeto FilterChain (es uno de los parámetros de doFilter), si no hay más filtros, entonces el request llega al servlet/jsp invocado (si ninguno de los filtros interrumpió el proceso).

 Los otros dos métodos que se tiene que implementar son "init()" (se ejecuta una vez al iniciar el filtro por el contenedor), y "destroy()" (se ejecuta una vez, cuando se destruye el filtro).

 A continuación, un ejemplo simple para ver el funcionamiento de los Filtros, que imprime una línea en la salida estándar.

==> Primero, la clase que implementa el filtro.
FiltroEjemplo.jsp
  package filtros;
import java.io.IOException;
import java.util.Date;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;

/* Se tiene que implementar Filter */
public class FiltroEjemplo implements Filter {
    public void doFilter(ServletRequest request, ServletResponse response,
            FilterChain chain)
throws IOException, ServletException {

 /* El codigo antes de llamar a chain.doFilter() se ejecuta antes de enviar el
   request al servlet o jsp correspondiente */

        HttpServletRequest reqst = (HttpServletRequest) request;
        System.out.println("Antes de doFilter(): " + new Date() + " - " + getClass().getName() + " "
                + reqst.getRequestURL());

        chain.doFilter(request, response);

 /* El codigo luego de chain.doFilter() se ejecuta después de la respuesta del servlet o jsp,
   y antes de llegar al cliente */
        System.out.println("Luego de doFilter(): " + new Date() + " - " + getClass().getName() + " "
                + reqst.getRequestURL());
    }

    public void destroy() {
    }
    public void init(FilterConfig filterConfig) {
    }
}

==> Se declara el filtro en el archivo web.xml
 web.xml 

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
    <filter>
        <filter-name>filtro1</filter-name>
        <filter-class>filtros.FiltroEjemplo</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>filtro1</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <servlet>
        <servlet-name>SrvltFiltroTst</servlet-name>
        <servlet-class>servlet.SrvltFiltroTst</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>SrvltFiltroTst</servlet-name>
        <url-pattern>/SrvltFiltroTst</url-pattern>
    </servlet-mapping>
    <welcome-file-list>
        <welcome-file>index.jsp</welcome-file>
    </welcome-file-list>
</web-app>

 Los dos elementos usados para declarar el filtro son: filter y filter-mapping

 En el elemento 'filter' se tiene que indicar el nombre del filtro con filter-name (cualquier nombre válido),
y la clase (nombre totalmente cualificado de la clase) que implementa el filtro.
     <filter>
        <filter-name>filtro1</filter-name>
        <filter-class>filtros.FiltroEjemplo</filter-class>
    </filter>

 Una vez que se le dio el nombre al filtro, se tiene que indicar cuando se ejecuta. Para esto usamos filter-mapping, en donde se tiene que indicar el nombre del filtro que estamos 'mapeando' con filter-name, y luego tenemos dos opciones, asociar el filtro con un patrón url con url-pattern, de esta forma es posible asociar el filtro con paginas, grupos de servlets, etc.
  En nuestro ejemplo usamos el patron "/*", por lo que se ejecuta el filtro toda vez que se invoca la aplicación ya que se mapea con cualquier url ingresada, (por ejemplo, se ejecuta el filtro al ingresar url's del tipo: /index.jsp  /reportes/nuevo.jsp   /SrvltFiltroTst )
    <filter-mapping>
        <filter-name>filtro1</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

 También es posible asociar el filtro con un servlet específico usando el elemento servlet-name.
 Para el web.xml indicado anteriormente, se podría escribir el filter-mapping de la siguiente forma:
    <filter-mapping>
        <filter-name>filtro1</filter-name>
       
<servlet-name>SrvltFiltroTst</servlet-name>
    </filter-mapping>
 En este caso, solo se ejecuta el filtro al invocar el servlet "SrvltFiltroTst".

 Al ejecutar la aplicación web con el filtro y configuración anterior (también imprimiendo una línea de el servlet y la pagina usada para la prueba), podemos ver en la salida estándar:

 Antes de doFilter(): Fri Jul 10 23:09:36 UYT 2009 - filtros.FiltroEjemplo http://localhost:8084/FiltroTestBlog/SrvltFiltroTst
  Fri Jul 10 23:09:36 UYT 2009 - servlet.SrvltFiltroTst
  Fri Jul 10 23:09:36 UYT 2009 - org.apache.jsp.index_jsp
 Luego de doFilter(): Fri Jul 10 23:09:36 UYT 2009 - filtros.FiltroEjemplo http://localhost:8084/FiltroTestBlog/SrvltFiltroTst

 Con este sencillo ejemplo podemos comprobar el proceso normal que se menciono al comienzo: cliente -> filtro -> jsp/servlet ->filtro ->cliente

Orden de ejecución de filtros en cadena.
  Cuando un request concuerda con varios filter-mapping, todos los filtros se ejecutan en un orden dado, según la siguiente regla.
 1) Todos los filtros que concuerden con el url-pattern , son colocados al comienzo de la cadena, y en el orden como fueron declarados en el archivo web.xml.
2) Luego se agregan a la cadena los filtros que concuerden con servlet-name , en el orden como fueron declarados.


 En otra oportunidad vamos a dar algún ejemplo más complejo, y ver la opción del elemento 'dispatcher' dentro de filter-mapping

 un recurso para ver más sobre este tema:  http://java.sun.com/products/servlet/Filters.html

1 comentario:

Anónimo dijo...

Muchas gracias por la explicacion del funcionamiento de Filtros, ahora si lo he entendido :-)