fundamentos de rup

54
Programa de Actualización Programa de Actualización Profesional Profesional Ingeniería de Sistemas - Ingeniería de Sistemas - EPE EPE Desarrollo para Desarrollo para Entorno Web Entorno Web Unidad 3: Capa de presentación

Upload: ymlfca

Post on 24-Jul-2015

278 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Fundamentos de RUP

Programa de Actualización Programa de Actualización ProfesionalProfesionalIngeniería de Sistemas - EPEIngeniería de Sistemas - EPE

Desarrollo para Entorno Desarrollo para Entorno WebWebUnidad 3: Capa de presentación

Page 2: Fundamentos de RUP

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/232

ÍndiceÍndice

Patrón MVC

Servlets / JSP

Frameworks MVC

AJAX

Page 3: Fundamentos de RUP

PATRÓN MVCPATRÓN MVC

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/233

Page 4: Fundamentos de RUP

Patrón MVCPatrón MVC

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/234

Page 5: Fundamentos de RUP

MVCMVC

ContextoEn sistemas que tienen interfaces de usuarios, suceden los siguientes escenarios:

• El sistema tiene que aceptar datos desde el cliente, actualizar la base de datos y devolver datos al usuario.

• Hay distintas maneras en que los datos pueden ser aceptados del usuario y entregados a los usuarios del sistema.

• Los datos que son proporcionados al sistema de una manera, deberían ser recuperables de otra manera.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/235

Page 6: Fundamentos de RUP

MVCMVC

Problemas al no utilizar MVCSi el cliente interactúa directamente con un componente de negocio, entonces algún cambio en el flujo de la aplicación obligaría a modificar las interfaces del cliente.

Si el sistema mantiene un solo componente que interactúa con el usuario y con la base de datos, entonces un nuevo requisito para soportar otro tipo de interfaz de usuario obligaría a rediseñar el componente.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/236

Page 7: Fundamentos de RUP

MVCMVC

ConsideracionesDado el contexto y el problema, se observa lo siguiente:

Existen 3 tareas a realizar:• Manejar las interacciones del usuario con el sistema.• Manejar los datos actuales.• Presentar los datos de múltiples formas al usuario.

Por lo tanto, si existe un solo componente que maneja todas esas tareas se debe de partir en 3 componentes.

Cada uno de los 3 componentes pueden ser manejados en diferentes componentes.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/237

Page 8: Fundamentos de RUP

MVCMVC

SoluciónLa solución es separar la representación de los datos del almacenamiento de los mismos y tener un tercer componente que coordine los dos primeros.

Estos 3 componentes son llamados Modelo, Vista y Controlador, y ellos forman el patrón de diseño MVC.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/238

Page 9: Fundamentos de RUP

MVCMVC

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/239

Page 10: Fundamentos de RUP

MVC - ELEMENTOSMVC - ELEMENTOS

MODELO: Es el responsable de mantener los datos o el estado de la aplicación. Notifica a las Vistas cuando los datos cambian.

VISTA: Contiene la lógica de la presentación. Muestra los datos que contiene en el Modelo a los usuarios. También permite al usuario interactuar con el sistema y notificar al Controlador de las acciones de los usuarios.

CONTROLADOR: Controla el flujo de la aplicación. Usa el Modelo y la Vista y las asocia. Puede usar múltiples Vistas y múltiples Modelos. El controlador recibe las acciones del cliente y las asocia a un modelo.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2310

Page 11: Fundamentos de RUP

MVCMVC

Consecuencias/ImplicanciasSeparar el almacenamiento de los datos (Modelo) de la presentación de los datos (Vista) permite tener múltiples Vistas para los mismos datos.

Los cambios pueden ocurrir en los componentes de la Vista y el Modelo independientemente. Cualquier cambio en cualquiera de los componentes no debe afectar al otro.

Incrementa la mantenibilidad y la extensibilidad del sistema.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2311

Page 12: Fundamentos de RUP

MVCMVC

Consecuencias/ImplicanciasSeparando el comportamiento de la aplicación (Controlador) de la presentación de los datos (Vista) permite al Controlador crear una Vista apropiada para un Modelo específico.

Separando el comportamiento de la aplicación (Controlador) del almacenamiento de los datos (Modelo) permite a las peticiones del usuario mapear a una función específica del Modelo.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2312

Page 13: Fundamentos de RUP

SERVLETS / JSPSERVLETS / JSP

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2313

Page 14: Fundamentos de RUP

ServletsServlets

Un Servlet es una Clase de Java que se ejecuta en el Web Container (llamado también contenedor de Servlets).

La especificación de Servlet proporciona un estándar y un framework independiente de la plataforma para la comunicación entre los servlets y contenedores.

Este framework es un conjunto de Clases e Interfaces.

Estas Clases e Interfaces conforman el Servlet API.

Un servlet puede manejar múltiples requerimientos de concurrencia y puede sincronizarlos.

Los servlets pueden redireccionar los requerimientos a otros servlets.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2314

Page 15: Fundamentos de RUP

Servlet APIServlet API

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2315

Page 16: Fundamentos de RUP

Ciclo de Vida de un ServletCiclo de Vida de un Servlet

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2316

Page 17: Fundamentos de RUP

Ciclo de Vida de un ServletCiclo de Vida de un Servlet

Carga e inicialización del Servlet

En forma predeterminada la clase HttpServlet inicializa el Servlet.

Para adicionar una inicialización personalizada se debe sobreescribir el método init().

Servicio del Servlet

Atiende a las peticiones POST o GET de los clientes. El método service() invoca a doPost() o doGet(), según sea el caso.

Destrucción el Servlet

El método destroy() destruye el servlet.

Para destruir algún recurso específico del Servlet se debe sobreescribir el método destroy().

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2317

Page 18: Fundamentos de RUP

Interface ServletInterface Servlet

La interface Servlet es la central abstracción del Servlet API.

Todos los Servlet se implementan de esta interface, en forma directa o indirecta (a través de la clase extendida HttpServlet )

Cuando un Servlet acepta un requerimiento desde un cliente recibe 2 objetos:

ServletRequest: Encapsula la comunicación del cliente al servidor.

ServletResponse: Encapsula la comunicación del servidor al cliente.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2318

Page 19: Fundamentos de RUP

Interface ServletInterface Servlet

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2319

Page 20: Fundamentos de RUP

Interface ServletRequestInterface ServletRequest

La interface ServletRequest permite al Servlet acceder a :

Información enviada por el cliente.

El protocolo usado por el cliente.

El nombre del cliente, dirección IP, navegador utilizado.

Suministra el flujo de entrada de ServletInputStream.

Las interfaces que se extienden de la interface ServletRequest permiten obtener más información de un protocolo específico.

La interface HttpServletRequest contiene métodos para acceder a la información de cabecera del HTTP.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2320

Page 21: Fundamentos de RUP

Interface HttpServletRequestInterface HttpServletRequest

Acceso a datos del cliente :El método getParameter() retorna el valor de un parámetro y lo almacena como String.

El método getParameterValues() retorna los valores de los varios parámetros (checkboxes, listas desplegables múltiples) y lo almacena en un String[].

El método getParameterNames() provee los nombres de los parámetros y lo almacena un java.util.Enumeration.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2321

Page 22: Fundamentos de RUP

Interface HttpServletRequestInterface HttpServletRequest

Método HTTP GET

Es utilizado para recuperar un recurso.

También para enviar información en texto plano al Servlet.

La información enviada por URL utiliza GET:• http://localhost/TestServlet?id=drodriguez

Los hiperenlaces utilizan GET.

Método HTTP POST

Utilizado para enviar datos al Servlet (texto plano o documentos)

Se configura en los formularios:• <form method=“post”>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2322

Page 23: Fundamentos de RUP

Interface ServletResponseInterface ServletResponse

La interface ServletResponse provee los métodos para contestar al cliente:

Suministra un flujo de salida ServletOutputStream y un Writer a través del cual el Servlet puede enviar datos al cliente.

Permite al Servlet configurar el tipo MIME (Multipurpose Internet Mail Extension) a enviar.

Las interfaces que se extienden de la interface ServletResponse permiten aumentar las capacidades de un protocolo específico.

La interface HttpServletResponse contiene métodos que permiten manipular la información de cabecera del HTTP.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2323

Page 24: Fundamentos de RUP

Interface Interface HttpServletResponseHttpServletResponse

El objeto HttpServletResponse provee dos formas de enviar datos al cliente :

El método getWriter() que retorna un objeto PrintWriter. Este objeto le permite al Servlet enviar texto plano (como HTML) al cliente.

El método getOutputStream() que retorna un objeto ServletOutputStream. Este objeto le permite al Servlet enviar datos en binario (doc, pdf, exe, ppt, zip, entre otros) al cliente.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2324

Page 25: Fundamentos de RUP

Session TrackingSession Tracking

El seguimiento de sesiones es necesario para mantener el estado entre el Servlet y el cliente que persiste en múltiples conexiones durante un tiempo determinado.

El seguimiento de sesiones se realiza de las siguientes formas:

Cookies

URL Rewriting

Hidden Fields

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2325

Page 26: Fundamentos de RUP

Session TrackingSession Tracking

¿Cómo el servidor puede mantener una sesión con un cliente si el HTTP no proporciona ningún mecanismo de recordar al cliente?

Cuando el servidor recibe la primera petición del cliente, el servidor inicia una sesión y le asigna un identificador único.

El cliente debe incluir este identificador único en cada requerimiento subsiguiente. El servidor inspecciona el identificador y asocia la petición con la correspondiente sesión.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2326

Page 27: Fundamentos de RUP

Session TrackingSession Tracking

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2327

Page 28: Fundamentos de RUP

Session TrackingSession Tracking

Cookies

Consiste en almacenar ese ID de sesión en una cookie del cliente:

• JSESSIONID=61C4F23524521390E70993E5120263C6

URL Rewriting

Consiste en agregar el ID en la URL. Es utilizado cuando el soporte a cookies ha sido deshabilitado.

<a href= "/ReportServlet;JSESSIONID=C084B32241B58114"> Reporte </a>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2328

Page 29: Fundamentos de RUP

Session TrackingSession Tracking

Hidden FieldsConsiste en agregar el ID en campos ocultos de HTML:

• <input type=“hidden” name=“JSESSIONID” value=“C084B32241B58114”/>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2329

Page 30: Fundamentos de RUP

HttpSessionHttpSession

El Servlet API trae el soporte de sesiones en la interfase javax.servlet.http.HttpSession.

El contenedor de Servlet crea un nuevo objeto HttpSession cuando inicia una sesión para un cliente.

Además de representar la sesión, este objeto actúa como un contenedor para la información relacionada a la sesión.

Normalmente, se necesitan hacer 3 acciones con una sesión HTTP:

Recuperar la sesión asociada con la petición.

Agregar o remover atributos de sesión.

Cerrar o invalidar la sesión si es necesario.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2330

Page 31: Fundamentos de RUP

HttpSessionHttpSession

Usualmente, un cliente no ofrece ningún indicador de que ha terminado la sesión. En este caso, el servidor nunca sabrá si el cliente ha terminado la sesión o no.

Para ayudarnos en este trabajo, el contenedor cerrará automáticamente la sesión después de un cierto periodo de tiempo de inactividad del usuario.

Este período de tiempo es configurado en minutos en el web.xml.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2331

Page 32: Fundamentos de RUP

HttpSessionHttpSession

Recuperar la sesión:HttpSession session = request.getSession();

Agregar un objeto a la sesión:session.setAttribute(NOMBRE, OBJETO);

Recuperar un objeto de la sesión:Object lista = (Object)session.getAttribute(NOMBRE);

Invalidando una sesión:session.invalidate();

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2332

Page 33: Fundamentos de RUP

HttpSessionHttpSession

Tiempo de expiración de la sesión

La configuración se realiza en el web.xml. El tiempo establecido está en MINUTOS. El valor 0 indicaría que la sesión nunca expirará.

<web-app>

<session-config>

<session-timeout>30</session-timeout>

</session-config>

</web-app>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2333

Page 34: Fundamentos de RUP

JSPJSP

JSP (JavaServer Pages) son páginas que contienen HTML y códig Java.

Tiene la extensión .jsp

JSP y Servlet pueden trabajar conjuntamente.

Los elementos de un JSP son:

Expression

Scriptlet

Declaration

Directive

ActionUPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2334

Page 35: Fundamentos de RUP

JSP - ExpressionJSP - Expression

Las expresiones son evaluadas y convertidas a String (java.lang.String).

Una vez evaluadas son agregadas a un objeto out JspWriter.

Equivalente a out.println();

Permite simplificar el código de salida o impresión de datos.

Representado por el caracter =

Sintaxis: <%= expresión %>

Ejemplo: <%= nombres %>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2335

Page 36: Fundamentos de RUP

JSP - ScriptletJSP - Scriptlet

Permiten insertar código Java dentro de código HTML.

Están representados por los caracteres <% (para inicio de bloque java) y %> (para fin de bloque java).

Sintaxis: <% código_java %>

Ejemplo:

<%

String mensaje = “Tecsup - Java Web”;

out.println(”<h1>" + mensaje + ”</h1>”);

%>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2336

Page 37: Fundamentos de RUP

JSP - DeclarationJSP - Declaration

Permiten crear sentencias de código Java que sólo serán ejecutadas al inicializarse el JSP.

Permite inicializar variables utilizadas en la página JSP.

Representadas por el caracter !

Sintaxis:

<%! modificador tipodato variable=valor; %>

Ejemplo:

<%! private int contador=0; %>

...

<% contador++; %>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2337

Page 38: Fundamentos de RUP

JSP - DeclarationJSP - Declaration

Define información que estará disponible en el JSP.

Existen diferentes directivas: page, include, taglib.

Afecta directamente a la compilación de la página JSP.

En caso no se defina ningún atributo de la directiva page, el compilador utilizará los valores predeterminados de los atributos.

Sintaxis: <%@ directiva atributo="valor" %>

Ejemplo: <%@ page language="java" %>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2338

Page 39: Fundamentos de RUP

JSP - ActionJSP - Action

Proporcionan funcionalidades incorporadas para desarrollar fácilmente aplicaciones Web.

Los Actions son etiquetas XML.

<jsp:include>

<jsp:param>

<jsp:forward>

<jsp:plugin>

<jsp:fallback>

<jsp: getProperty>

<jsp:setProperty>

`<jsp:useBean>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2339

Page 40: Fundamentos de RUP

JSP - ELJSP - EL

EL (Lenguaje de Expresiones) es independiente de la especificación JSP, aunque se incluye en ella.

Facilita la escritura de páginas JSP.

Ejemplo: ${ variable }

Son evaluados cuando se compila la página.

Se pueden realizar operaciones matemáticas, relacionales, lógicos, condiciones, entre otros.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2340

Page 41: Fundamentos de RUP

JSP - ELJSP - EL

En EL se puede acceder a algunos objetos implícitos:

pageScope: Variables de ámbito de página

requestScope: Variables de ámbito de request.

sessionScope: Variables de ámbito sesión.

applicationScope: Variables de ámbito application (contexto).

param: Parámetros del request como cadenas.

paramValues: Parámetros del request como array de cadenas.

cookie: Valores de las cookies recibidas en el request.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2341

Page 42: Fundamentos de RUP

Custom tagsCustom tags

La tecnología JSP nos permite incluir etiquetas personalizadas a través de una librería de etiquetas.

Las etiquetas personalizadas nos permiten encapsular lógica de la aplicación y reutilizarla en los JSP.

Una etiqueta es una clase Java que implementa una interface especializada.

Para definir un Tag simple debemos implementar la interfase Tag.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2342

Page 43: Fundamentos de RUP

JavaBeansJavaBeans

Son componentes de software escritos en Java.

Encapsulan lógica y métodos para funcionalidades específicas.

Los JavaBeans debe cumplir las siguientes características:

Atributos privados

Métodos públicos set y get

Constructor vacío

Las acciones que se utilizan para JavaBeans son:<jsp:useBean>

<jsp:setProperty>

<jsp:getProperty>

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2343

Page 44: Fundamentos de RUP

FRAMEWORKS MVCFRAMEWORKS MVC

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2344

Page 45: Fundamentos de RUP

Características comunesCaracterísticas comunes

Un framework es un software que proporciona funcionalidad genérica y que puede ser sobreescrita o extendida para obtener una funcionalidad específica.

Los frameworks Web proporcionan un conjunto de Clases e Interfaces para implementar la capa de presentación del software.

Para Java, existen diferentes frameworks, entre ellos: Struts, JSF y Spring MVC. Estos tres frameworks:

Implementan MVC

De libre uso y amplia documentación

Integración con otros frameworks y librerías.

Amplio apoyo de la comunidad

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2345

Page 46: Fundamentos de RUP

StrutsStruts

Combina las tecnologías de los Servlets y JSP.

Sus componentes principales son: Actions, Interceptors, Result Types, View Tecnologies, Value Stack / OGNL.

El Controlador es implementado por un Filter Servlet, igual que los interceptors. Mantiene el flujo de la aplicación en XML.

La Vista puede ser implementada con JSP usando etiquetas JSTL, ONGL, EL.

El Modelo está implementado por unas clases llamadas Actions que son simplemente POJO’s.

Se integra con Spring Framework.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2346

Page 47: Fundamentos de RUP

StrutsStruts

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2347

Page 48: Fundamentos de RUP

JSFJSF

Es una especificación estándar de JavaEE.

Existen diferentes implementaciones de los fabricantes:

JSF Reference Implementation de Sun Microsystems.

MyFaces de Apache Software Foundation

Rich Faces

ICEfaces

Simplifica el desarrollo de interfaces de usuario.

Utiliza JSP para mostrar las páginas

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2348

Page 49: Fundamentos de RUP

Spring MVCSpring MVC

Spring es un framework de código abierto para el desarrollo de aplicaciones Java.

Spring MVC es el módulo que permite implementar la capa de presentación.

Ofrece una clara división entre el Controlador, Vista y Modelo.

Es muy flexible, implementa su estructura mediante interfaces.

Provee interceptores como controladores.

Los controladores se configuran mediante inversión de control.

Se integra a diferentes Vistas: JSP/JSTL, Tiles, Velocity, FreeMarker, entre otros.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2349

Page 50: Fundamentos de RUP

AJAXAJAX

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2350

Page 51: Fundamentos de RUP

AJAXAJAX

El término AJAX es un acrónimo de Asynchronous JavaScript and XML, que se puede traducir como “JavaScript y XML asíncrono”.

AJAX no es una tecnología en sí mismo. En realidad, se trata de la unión de varias tecnologías que se desarrollan de forma autónoma y que se unen para darle mayores funcionalidades a las aplicaciones Web.

Tecnologías y lenguajes relativos:XHTML y CSS: Para una presentación basada en estándares.

DOM: para la manipulación de la presentación.

XML, XSLT, JSON: Para el intercambio y manipulación de datos

Javascript (XMLHttpRequest): intercambio asíncrono de información y para integrar las demás tecnologías.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2351

Page 52: Fundamentos de RUP

AJAXAJAX

AJAX permite mejorar completamente la interacción del usuario con la aplicación, evitando las recargas constantes de la página, ya que el intercambio de información con el servidor se produce en un segundo plano.

Algunas aplicaciones con AJAX:

Validación de formularios en tiempo real

Auto-completar información

Operaciones maestro – detalle

Controles avanzados: árboles, menús, barras de progreso, zoom, mapas (Google). Todos ellos interactuando con la base de datos.

Refresco automático de datos

Notificaciones desde el servidor (PUSH)UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2352

Page 53: Fundamentos de RUP

AJAXAJAX

DOJO Toolkithttp://dojotoolkit.com/

Script.aculo.ushttp://script.aculo.us/

Yahoo UI Widgetshttp://developer.yahoo.com/yui/

Google Web Toolkit - Google Codehttp://code.google.com/webtoolkit/

Prototypehttp://prototype.conio.net/

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2353

Page 54: Fundamentos de RUP

BibliografíaBibliografía

Matthew Scarpino, Hanumant Deshmukh, Jignesh Malavia. SCWCD Exam Study Kit.

Marty Hall. Core Servlets and JavaServer pages.

Ian Roughley. Starting Struts 2.

Donald Brown, Chad Michael Davis, Scott Stanlick. Struts 2 in Action.

UPC - EPE - Ingeniería de Sistemas - Programa de Actualización Profesional 12/04/2354