Tema 1: JSP Básico

1.1. Introducción a JSP

JSP (JavaServer Pages) es una tecnología que permite incluir código Java en páginas web. El denominado contenedor JSP (que ser�a un componente del servidor web) es el encargado de tomar la página, sustituir el código Java que contiene por el resultado de su ejecución, y enviarla al cliente. Así, se pueden diseñar fácilmente páginas con partes fijas y partes variables. El siguiente es un ejemplo muy sencillo de página JSP:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>Mi primera página JSP</title>
</head>
<body>
<h1> Hoy es: <%= new java.util.Date() %> </h1>
</body>
</html>

Para ejecutar la página basta con colocarla en una aplicación web (por ejemplo, en Tomcat, dentro de webapps/ROOT). No es necesario que sea en un directorio específico como ocurre con los servlets, sino que puede ir en cualquier directorio en el que se colocaría normalmente un HTML.

La última versión de la especificaci�n JSP es la 2.0, aunque es de reciente aparición (Tomcat 4.x implementa la versión anterior, la 1.2, misma que cubre este tema). Como se ver�, es una especificaci�n paralela al API de servlets, concretamente a la versi�n 2.3. Se puede encontrar m�s informaci�n sobre JSP en

http://java.sun.com/products/jsp

Aunque JSP y servlets parecen a primera vista tecnologías distintas, en realidad el servidor web traduce internamente el JSP a un servlet, lo compila y finalmente lo ejecuta cada vez que el cliente solicita la página JSP. Por ello, en principio, JSPs y servlets ofrecen la misma funcionalidad, aunque sus características los hacen apropiados para distinto tipo de tareas. Los JSP son mejores para generar páginas con gran parte de contenido estático. Un servlet que realice la misma función debe incluir gran cantidad de sentencias del tipo out.println() para producir el HTML. Por el contrario, los servlets son mejores en tareas que generen poca salida, datos binarios o páginas con gran parte de contenido variable. En proyectos más complejos, lo recomendable es combinar ambas tecnologías: los servlets para el procesamiento de información y los JSP para presentar los datos al cliente.

1.2. Traducci�n de los JSP a servlets

Como se ha comentado, la primera vez que se solicita una p�gina JSP, el servidor genera el servlet equivalente, lo compila y lo ejecuta. Para las siguientes solicitudes, solo es necesario ejecutar el c�digo compilado. El servlet generado de manera autom�tica tiene un m�todo _jspService que es el equivalente al service de los servlets "generados manualmente". En este m�todo es donde se genera el c�digo HTML, mediante instrucciones println y donde se ejecuta el c�digo Java insertado en la p�gina. Por ejemplo, la p�gina primera.jsp podr�a generar un servlet con estructura similar al siguiente:

public void _jspService(HttpServletRequest request, 
                        HttpServletResponse  response)
                        throws java.io.IOException, ServletException {
   JspWriter out = null;
   response.setContentType("text/html;ISO-8859-1");
   out.println("<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.0        
                Transitional//EN\">);
   out.println("<html>");
   out.println("<head>");
   out.println("<title>Mi primera pagina JSP</title>");
   out.println("</head>");
   out.println("<body>");
   out.print("Hoy es ");
   out.println(new java.util.Date());
   out.println("</body>");
   out.println("</html>");
}

El directorio donde se coloca el servlet generado, as� como su nombre, dependen del servidor web. Por ejemplo, Tomcat utiliza su directorio work/localhost/aplicacion_web. En caso de que la p�gina est� en ROOT, el nombre de la aplicaci�n se sustituye por un car�cter de subrayado (_).

1.3. Elementos de JSP

Existen tres tipos de elementos JSP que podemos insertar en una p�gina web:

Se pueden poner comentarios en una p�gina JSP entre los s�mbolos <%-- y --%>. El contenedor JSP ignorar� todo lo contenido entre ambos. Dentro de los fragmentos de c�digo Java tambi�n se pueden colocar comentarios siguiendo la sintaxis habitual del lenguaje.

1.4. Inserci�n de c�digo en p�ginas JSP

Hay tres formas de insertar c�digo Java en una p�gina JSP:

1.4.1. Expresiones

Como se ha visto, se eval�an, su resultado se convierte a un String y se escriben en la salida (el objeto predefinido out). La forma de traducir una expresi�n a c�digo de servlet es imprimi�ndola en out (mediante una sentencia out.write(expresion)) o similar.

1.4.2. Scriptlets

Permiten ejecutar c�digo arbitrario, cuyo resultado no es necesario enviar a la salida. Si desde un scriptlet se desea escribir algo en �sta, bastar� con utilizar el objeto predefinido out. Un uso com�n de los scriptlets es hacer que ciertas partes de c�digo HTML aparezcan o no en funci�n de una condici�n. Por ejemplo:

<%
  java.util.Calendar ahora = java.util.Calendar.getInstance();
  int hora = ahora.get(java.util.Calendar.HOUR_OF_DAY);
%>
<b> Hola mundo, <i>
<% if ((hora>20)||(hora<6)) { %> 
     buenas noches
<% }  
   else if ((hora>=6)&&(hora<=12)) { %>
          buenos d�as
<%      }
	else { %> 
           buenas tardes
<%      } %>
</i> </b>

1.4.3. Declaraciones

Permiten definir variables o m�todos que se insertar�n dentro del cuerpo del servlet generado. Esto da la posibilidad de sobreescribir los m�todos jspInit y jspDestroy que son el equivalente en JSP del init y destroy de los servlets. Las variables declaradas conservar�n su valor entre sucesivas llamadas a la p�gina, ya que son variables miembro del servlet y no locales al m�todo jspService. Esto nos permite, por ejemplo, crear un contador de accesos a la p�gina:

<%! private int accesos = 0; %>
<h1> Visitas: <%= ++accesos %> </h1>

1.4.4. Objetos impl�citos de JSP

En cualquiera de estas tres formas, se puede hacer referencia a una serie de objetos impl�citos , que se corresponden con objetos �tiles del API de servlets (petici�n, respuesta, ...) y que en realidad son variables instanciadas de manera autom�tica en el servlet generado a partir del JSP. Los objetos predefinidos en JSP se referencian en la tabla 1.

Objeto Significado
request el objeto HttpServletRequest asociado con la petici�n
response el objeto HttpServletResponse asociado con la respuesta
out el Writer empleado para enviar la salida al cliente. La salida de los JSP emplea un buffer que permite que se env�en cabeceras HTTP o c�digos de estado aunque ya se haya empezado a escribir en la salida (out no es un PrintWriter sino un objeto de la clase especial JspWriter).
session el objeto HttpSession asociado con la petici�n actual. En JSP, las sesiones se crean autom�ticamente, de modo que este objeto est� instanciado aunque no se cree expl�citamente una sesi�n.
application el objeto ServletContext, com�n a todos los servlets de la aplicaci�n web.
config el objeto ServletConfig, empleado para leer par�metros de inicializaci�n.
pageContext permite acceder desde un �nico objeto a todos los dem�s objetos impl�citos
page referencia al propio servlet generado (tiene el mismo valor que this).Como tal, en Java no tiene demasiado sentido utilizarla, pero est� pensada para el caso en que se utilizara un lenguaje de programaci�n distinto.
exception Representa un error producido en la aplicaci�n. Solo es accesible si la p�gina se ha designado como p�gina de error (mediante la directiva page isErrorPage).
Tabla 1: Objetos impl�citos de JSP.

1.5. Directivas de p�gina

Las directivas influyen en la estructura que tendr� el servlet generado a partir de la p�gina JSP. Hay tres tipos de directivas:

El formato genérico de una directiva es:

<%@ directiva atributo="valor" %>

algunas directivas admiten más de un atributo.

1.5.1. La directiva page

La tabla 2 recoge los distintos atributos que admite la directiva page y su significado.

Tabla 2: atributos de la directiva page
Atributo Significado Ejemplo
import el equivalente a una sentencia import de Java <%@ page import="java.util.Date" %>
contentType genera una cabecera HTTP Content-Type <%@ page contentType="text/plain" %>
isThreadSafe si es false, el servlet generado implementará el interface SingleThreadModel (ún único hilo para todas las peticiones). Por defecto, el valor es true.  
session Si es false, no se creará un objeto session de manera automática. Por defecto, es true.  
buffer Define el tamaño del buffer para la salida (en kb), o none si no se desea buffer. Su existencia permite generar cabeceras HTTP o códigos de estado aunque ya se haya comenzado a escribir la salida. <%@ page buffer="64kb" %>
autoflush Si es true (valor por defecto), el buffer se env�a autom�ticamente a la salida al llenarse. Si es false, al llenarse el buffer se genera una excepci�n.  
extends Permite especificar de qu� clase debe descender el servlet generado a partir de la p�gina JSP. No es habitual cambiarlo.  
info define una cadena que puede obtenerse a trav�s del m�todo getServletInfo <%@ page info="carro de la compra" %>
errorPage especifica la p�gina JSP que debe procesar los errores generados y no capturados en la actual. <%@ page errorPage="error.jsp" %>
isErrorPage Si es true, indica que la p�gina act�a como p�gina de error para otro JSP. El valor por defecto es false.  
language Permite especificar el lenguaje de programaci�n usado en el JSP. En la pr�ctica, el lenguaje siempre es Java, por lo que esta directiva no se usa.  
pageEncoding define el juego de caracteres que usa la p�gina. El valor por defecto es ISO-8859-1.  

1.6. Acciones

En JSP existen varios mecanismos para incluir elementos externos en la p�gina actual o redirigir la petici�n hacia otra p�gina

1.6.1. La directiva include

Es el equivalente al #include del lenguaje C. su sintaxis es:

<%@ include file="fichero" %>

Como el c�digo se incluye en el servlet generado, los fragmentos de c�digo incluidos pueden tener efecto sobre la p�gina actual. As�, se puede utilizar esta directiva para definir constantes, generar cabeceras HTTP, ...

El problema de esta directiva es que el est�ndar no exige que el contenedor JSP detecte de manera autom�tica los cambios en los ficheros incluidos, de manera que si cambia uno de ellos puede ser necesario forzar la recompilaci�n de las p�ginas JSP que los incluyan.

La especificaci�n JSP recomienda que si la p�gina incluida no es una p�gina JSP v�lida por s� sola (por ejemplo, porque utiliza variables que se conf�a que se hayan declarado previamente) se utilice la extensi�n "est�ndar" .jspf (JSP fragment) y se coloque en un directorio no p�blico del contenedor JSP (por ejemplo, WEB-INF, que no es accesible desde el cliente, pero s� desde la directiva).

1.6.2. La acci�n <jsp:include>

Esta acci�n incluye en una p�gina la salida generada por otra perteneciente a la misma aplicaci�n web. La petici�n se redirige a la p�gina incluida, y la respuesta que genera se incluye en la generada por la principal. Su sintaxis es:

<jsp:include page="URL relativa" flush="true|false"/>

El atributo flush especifica si el flujo de salida de la p�gina principal deber�a ser enviado al cliente antes de enviar el de la p�gina incluida. En JSP 1.2 este atributo es optativo, y su valor por defecto es false. En JSP 1.1 es obligatorio y siempre deb�a valer true (el forzar el vaciado de buffer era problem�tico porque una vez que ha sucedido esto no se pueden hacer redirecciones ni ir a p�ginas de error, ya que ya se han terminado de escribir las cabeceras).

Esta acci�n presenta la ventaja sobre la directiva del mismo nombre de que cambios en la p�gina incluida no obligan a recompilar la "principal". No obstante, la p�gina incluida solo tiene acceso al JspWriter de la "principal" y no puede generar cabeceras (por ejemplo, no puede crear cookies).

Por defecto, la petici�n que se le pasa a la p�gina incluida es la original, pero se le pueden agregar par�metros adicionales, mediante la etiqueta jsp:param. Por ejemplo:

<jsp:include page="cabecera.jsp">
   <jsp:param name="color" value="YELLOW" />
</jsp:include>

1.6.3. La acci�n <jsp:plugin>

Esta acci�n sirve para incluir, de manera portable e independiente del navegador, applets que utilicen alguna librer�a de Java 2 (Swing, colecciones, Java 2D, ...), ya que las m�quinas virtuales Java distribuidas con algunos navegadores relativamente antiguos (Explorer 5.x, Netscape 4.x,...) son de una versi�n anterior a Java 2.

1.6.4. La acci�n <jsp:forward>

Esta acci�n se utiliza para redirigir la petici�n hacia otra p�gina JSP que est� en la misma aplicaci�n web que la actual. Un ejemplo de su sintaxis b�sica es:

<jsp:forward page="principal.jsp"/>

La salida generada hasta el momento por la página actual se descarta (se borra el buffer). En caso de que no se utilizara buffer de salida, se produciría una excepción.

Al igual que en el caso de <jsp:include>, se pueden a�adir par�metros a la petici�n original para que los reciba la nueva p�gina JSP:

<jsp:forward page="principal.jsp">
   <jsp:param name="privilegios" value="root" />
</jsp:forward>