lunes, 8 de julio de 2013

1.2.10 Session Facade

Proporciona una interfaz unificada para un conjunto de interfaces de un subsistema. Define una interfaz de alto nivel que hace que el subsistema sea más fácil de usar.


El patrón fachada viene motivado por la necesidad de estructurar un entorno de programación y reducir su complejidad con la división en subsistemas, minimizando las comunicaciones y dependencias entre éstos.

Características
Ø Crea una fachada para encapsular las complejas interrelaciones de los distintos elementos de negocio.

Ø Proporciona un servicio uniforme y maneja el flujo de ejecución de los subelementos.

Ventajas

Una de las ventajas de utilizar este patrón a la hora de controlar los permisos de los usuarios. Cada usuario tiene un rol (administrador, invitado, usuario registrado, etc.) y, para controlar los permisos de cada rol, lo único que hay que hacer es definir las operaciones de cada rol en distintos sesión beans de la capa de control y después, desde el deployment descriptor de los EJBs, mapear nuestros roles con dichos sesión beans. La autenticación se realiza en la capa de interfaz.


Desventajas.
Ø Oculta a los clientes los componentes del subsistema, reduciendo así el número de objetos con los que tratan los clientes y haciendo que el subsistema sea más fácil de usar.

Ø Promueve un débil acoplamiento entre el subsistema y sus clientes. Muchas veces los componentes de un subsistema sin que sus clientes se vean afectados, las fachadas ayudan a estructurar en capas un sistema y las dependencias entre los objetos. También pueden eliminar dependencias complejas o circulares. Esto puede ser una consecuencia importante cuando el cliente y el subsistema se implementan por separado.

En los grandes sistemas de software es vital reducir las dependencias de compilación. Queremos ahorrar tiempo minimizando la recopilación cuando cambien las clases del subsistema. Reducir las dependencias de compilación con fachada puede limitar la compilación necesaria para un pequeño cambio en un subsistema importante. Una fachada puede simplificar portar sistemas en otras plataformas ya que es menos probable que construir un subsistema requiera volver a construir todos los otros.
Ø No impiden que las aplicaciones usen las clases del subsistema en caso de que sea necesario. De este modo se puede elegir entre la facilidad de uso y generalidad.

Estructura




Participantes 


Ø Client (EJBAccountFacadeDelegate)

Puede ser un Business Delegate u otro Session Facade

Ø SessionFacade (AccountFacadeEJB)

Normalmente, un Session Bean p
roporciona un interfaz sencillo al cliente, ocultando las  relaciones entre numerosos objetos de negocioSession Facade (7)


Participantes (cont)

Ø Business Object (Account y AccountOperation)

Proporciona datos (Entity Bean o DAO) o un servicio (SessionBean)

A la hora de implementar una fachada deben tenerse en cuenta los siguientes aspectos:


Ø Reducción del acoplamiento cliente-subsistema. El acoplamiento entre clientes y el subsistema puede verse reducido todavía más haciendo que Fachada sea una clase abstracta con subclases concretas para diferentes implementaciones de un subsistema. De esa manera los clientes pueden comunicarse con el subsistema a través de la interfaz de una clase abstracta Fachada. Este acoplamiento abstracto evita que los clientes tengan que saber que implementación de un subsistema están usando.
Ø Clases del subsistema del subsistema públicas o privadas. Un subsistema se parece a una clase en que ambos tienen interfaces y los dos encapsulan algo – una clase encapsula estado y operaciones, mientras que un subsistema encapsula clases. Y del mismo modo resulta útil pensar en la interfaz pública y privada de una clase, también podemos pensar en la interfaz pública y privada de un subsistema.

Ø La interfaz pública de un subsistema consiste en una serie de clases a las que acceden todos los clientes; la interfaz privada es solo para quienes vayan a ampliar el subsistema. La clase fachada es parte de la interfaz pública, por supuesto pero no es la única. Otras clases del subsistema también suelen ser públicas.

1.2.11 Transfer Object

Java 2 Platform, Enterprise Edition (J2EE) implementan componentes de negocio del lado del servidor como beans de sesión y beans de entidad. Algunos métodos expuestos por los componentes de negocio devuelven datos al cliente. A menudo, el cliente invoca métodos get de un objeto de negocio varias veces hasta obtener todos los valores de los atributos.

Los beans de sesión representan los servicios a las empresas y no se comparten entre los usuarios. Un bean de sesión proporciona métodos de servicios de granularidad gruesa cuando se implementa por el patrón Session Facade.

Los beans de entidad, por otro lado, son multiusuario, objetos transaccionales que representan datos persistentes. Un bean de entidad expone los valores de los atributos, proporcionando un método de acceso (también referido como un captador o método get ) para cada atributo que desea exponer.

Causas
Ø Todos los accesos a un bean enterprise se realizan mediante interfaces remotos. Cada llamada a un bean enterprise potencialmente es una llamada a un método remoto con sobrecarga de red.

Ø Normalmente, las aplicaciones tienen transacciones de lectura con mayor frecuencia que las de actualización. El cliente solicita los datos desde la capa de negocio para su presentación, y otros tipos de procesamientos de sólo-lectura. El cliente actualiza los datos de la capa de negocio con mucha menos frecuencia con la que los lee.

Solución
Utilizar un Transfer Object para encapsular los datos de negocio. Se utiliza una única llamada a un método para enviar y recuperar el Transfer Object. Cuando el cliente solicita los datos de negocio al bean enterprise, éste puede construir el Transfer Object, rellenarlo con sus valores de atributos y pasarlo por valor al cliente.

Ø Los clientes normalmente solicitan más de un valor a un bean enterprise. Para reducir el número de llamadas remotas y evitar la sobrecarga asociada, es mejor el Transfer Objects para transportar los datos desde el bean enteprise al cliente.

Ø Cuando un bean enterprise utiliza un Transfer Object, el cliente hace una sola llamada a un método remoto del bean enterprise para solicitar el Transfer Object en vez de numerosas llamadas remotas para obtener valores de atributos individuales

Estructura Transfer Object 


Ø Client

Representa al cliente del bean enterprise. El cliente puede ser una aplicación final de usuario, como es el caso de una aplicación que ha sido diseñada para acceder directamente a beans enterprise. El cliente puede utilizar Business Delegate u otro BusinessObject diferente.
Ø BusinessObject

Representa un rol en este patrón que puede cumplir un bean de sesión, un bean de entidad, o un Data Access Object (DAO). BusinessObject es el responsable de crear el Transfer Object y devolverlo al cliente bajo pedido. El BusinessObject también podría recibir datos desde el cliente en la forma de un Transfer Object y utilizar esos datos para realizar una actualización.

Ø TransferObject

TransferObject es un objeto Java serializable referenciado como un Transfer Object. Una clase Transfer Object podría proporcionar un constructor que acepte todos los atributos requeridos para crear el Transfer Object. El constructor podría aceptar todos los valores de atributos del bean de entidad para el que se ha diseñado el Transfer Object

Diagrama de secuencia Transfer Object 



Consecuencias.

Ø Transfiere Más Datos en Menos Llamadas Remotas
En lugar de realizar múltiples llamadas sobre la red al BusinessObject para obtener los valores de los atributos, esta solución proporciona una sola llamada a un método.

Ø Reduce el Tráfico de Red
Un Transfer Object transfiere los valores desde el bean de entidad al cliente en una llamada a un método remoto. El Transfer Object actúa como un transportista de datos y reduce el número de llamadas remotas requeridas para obtener los valores de los atributos del bean; y esto significa un mejor rendimiento de la red.

1.2.12 Value List Handler

Contexto

El cliente le pide al servicio una lista de ítems para su presentación. El número de ítems de la lista no se conoce y puede ser muy grande en muchas circunstancias.

Causas

Ø La aplicación cliente necesita una facilidad de consulta eficiente para evitar tener que llamar al método ejbFind() de cada bean e invocar a cada objeto remoto devuelto.

Ø Se necesita una mecanismo de caché en la capa-servidor para servir a los clientes que no pueden recibir y procesar el cojunto de resultados completo.

Ø Se puede optimizar una consulta que se ejecuta repetidamente sobre unos datos razonablemente estáticos para proporcionar resultados más rápidos. Esto depende de la aplicación y de la implementación de este patrón.

Problema
La mayoría de las aplicaciones de la plataforma J2EE tienen un requerimiento de búsqueda y consulta para buscar y listar ciertos datos. En algunos casos, dichas operaciones de búsqueda y consulta podrían traer resultados que pueden ser bastante grandes. No es práctico devolver toda la hoja de resultados cuando los requerimientos del cliente son moverese por los resultados, en vez de procesar el conjunto completo. Normalmente, un cliente usa los resultados de una consulta para propósitos de sólo-lectura, como mostrar una lista de resultados.

Muchas veces el cliente sólo ve los primeros registros que devuelve la búsqueda, y podría descargar los registros restantes e intentar otra nueva consulta. La práctica de obtener uns lista de valores representados en un bean de entidad llamando al método ejbFind(), que devuelve una collection de objetos remotos, y luego llamar a cada bean de entidad para obtener el valor, consume muchos recursos de red y se considera una mala práctica.

Ø La aplicación cliente necesita una facilidad de consulta eficiente para evitar tener que llamar al método ejbFind() de cada bean e invocar a cada objeto remoto devuelto.

Ø Se necesita una mecanismo de caché en la capa-servidor para servir a los clientes que no pueden recibir y procesar el cojunto de resultados completo.

Ø Se puede optimizar una consulta que se ejecuta repetidamente sobre unos datos razonablemente estáticos para proporcionar resultados más rápidos. Esto depende de la aplicación y de la implementación de este patrón.

Solución
Utilizar un Value List Handler para controlar la búsqueda, hacer un caché con los resultados, y proporcionar los resultados al cliente en una hoja de resultados cuyo tamaño y desplazamiento cumpla los requerimientos del cliente.

Estructura Value List Handler



Ø ValueListIterator

Este interface podría proporcionar la facilidad de iteración con los siguientes métodos de ejemplo:

  • o getSize() obtiene el tamaño de la hoja de resultados.
  • o getCurrentElement() obtiene el Transfer Object actual de la lista.
  • o getPreviousElements(int howMany) obtiene una colección de Transfer Objects que son anteriores en la lista al elemento actual.
  • o getNextElements(int howMany) obtiene una colección de Transfer Objects que son posteriores en la lista al elemento actual.
  • o resetIndex() reinicia el índice para ir al inicio de la lista.

Dependiendo de las necesidades, se pueden incluir otros métodos de conveniencia en el interface ValueListIterator.

Ø ValueListHandler


Este es el objeto que implementa el interface ValueListIterator. ValueListHandlerejecuta la consulta requerida cuando se lo solicita el cliente. Obtiene los resultados de la consulta, que maneja en una colección privada representada por el objeto ValueList.ValueListHandler crea y manipula la colección ValueList. Cuando el cliente solicita los resultados, ValueListHandler obtiene los Transfer Objects desde el ValueList cacheado, crea una nueva colección de Transfer Objects, serializa la colección y la envía de vuelta al cliente. ValueListHandler también sigue la pista del índice actual y del tamaño de la lista.

Ø DataAccessObject

ValueListHandler puede hacer uso de un DataAccessObject para mantener separada la implementación del acceso a la base de datos. DataAccessObject proporciona un API sencillo para acceder a la base de datos (o cualquier otro almacenamiento persistente), ejecuta consultas y recupera resultados.


Ø ValueList

ValueList es una colección (una lista) que contiene los resultados de la consulta. Los resultados se almacenan como objetos Transfer Objects. Si falla la consulta y no se devuelven resultados, entonces esta lista está vacía. El bean de sesión ValueListHandler puede almacenar ValueList para evitar repeticiones innecesarias de la consulta.

Ø TransferObject

TransferObject representa una vista de un registro individual de los resultados de la consulta. Es un objeto serializable no modificable que proporciona un espacio para los datos de los atributos de cada registro.

Diagrama de secuencia Value List Handler



Consecuencias


Ø Proporciona Alternativas a los métodos find() de EJB para Grandes Consultas

Ø Crea un Caché de Resultados de la Consulta en el Lado del Servidor
Se necesita cachear los resultados obtenidos de la ejecución de la consulta cuando un cliente debe mostrarlos en pequeñas partes en vez de una gran lista

Ø Proporciona una Mayor Flexibilidad de Consulta

1.2.13 View Helper

Este patrón se centra en diversificar las responsabilidades de nuestras aplicaciones.

Contexto

El sistema crea el contenido de la presentación, lo que requiere el procesamiento de datos de negocio dinámicos.

Problema

La capa de presentación suele tender a realizar modificaciones constantemente. Si la lógica de negocio y el acceso a datos se mezclan con el formato de presentación, estos cambios son costosos y complejos de implementar. Mezclar la lógica de negocio y de sistema con el procesamiento de la vista reduce la modularidad y también proporciona una pobre separación de los roles entre los equipos de producción web y de desarrollo de software.

Solución


Basándonos en los principios del Modelo-Vista-Controlador, una vista delega sus responsabilidades de procesamiento en sus clases de ayuda, implementadas como JavaBeans o etiquetas personalizadas. Las clases de ayuda o Helpers también almacenan el modelo de datos intermedio de la vista y sirven como adaptadores de datos de negocio.


Delegar la lógica de negocio en otra capa externa a la de presentación hace que nuestra aplicación sea más modular y facilita la reutilización de componentes. Varios clientes, como controladores y vistas, podrían utilizar el mismo Helper para recuperar y adaptar estados del modelo similares para su presentación en varias vistas. De esta manera eliminamos redundancia en nuestros códigos.


El patrón View Helper se enfoca en recomendar formas de particionar las responsabilidades de nuestras aplicaciones.


Implementación y Participantes

Ø Cliente: Realiza la petición.


Ø View: Una vista representa y muestra información al cliente. La información que se muestra se recupera de un modelo. LosHelpers soportan Views encapsulando y adaptando un modelo para utilizarlo.


Ø Helper: Un Helper es el responsable de ayudar a la vista o al controlador a completar su procesamiento incluyendo la obtención de los datos requeridos por la vista y su almacenamiento en el modelo intermedio, en cuyo caso algunas veces nos podemos referir al Helper como un ValueBean.


Ø BussinesService: El servicio de negocio es un rol que cumple el servicio al que está accediendo el cliente.


Ø ValueBean: Un ValueBean es un otro nombre para un Helper que es responsable de contener el estado del modelo intermedio para que lo utilice una vista.

Diagrama de secuencia de View Helper


Capítulo 8 Patrones y principios de diseño



Un buen diseño orientado a objetos no sólo consiste en utilizar los elementos que se han explicado sin orden ni concierto, sino que juega un papel fundamental la experiencia del diseñador. Hay que encontrar las abstracciones adecuadas, construir interfaces eficaces y establecer las relaciones necesarias entre ellas.
Además, todo ello debe hacerse de manera específica para el problema que se pretende resolver, para que la programación ofrezca la ventaja de acercarse al dominio del problema. Por otro lado, y también debe hacerse de manera genérica, para que sea fácil incorporar nuevos requisitos o resolver problemas distintos con los mismos objetos.
En este tema se esboza el principio del camino que un diseñador de programas orientados a objetos debe recorrer. Para ello se introduce el concepto de Patrón de Diseño y se presentan unos cuantos de los más importantes. Posteriormente se enuncian algunos principios que ayudan a crear un buen diseño.

8.1. Principales Patrones de Diseño


Es un hecho que, en general, los diseñadores noveles no son capaces de hacer buenos diseños, pues no utilizan adecuadamente las herramientas que la Programación Orientada a Objetos proporciona. Mientras, los diseñadores experimentados se caracterizan por conocer multitud de buenas soluciones a problemas que ya han tenido que resolver, y reutilizan estas soluciones adaptándolas a los nuevos problemas que abordan.
Los Patrones de Diseño intentan capturar esa experiencia en un conjunto de diseños genéricos que sean aplicables a un sin fin de problemas. Según Christopher Alexander, destacado arquitecto del siglo XX, “cada patrón de diseño describe un problema que ocurre una y otra vez en nuestro entorno, así como la solución a ese problema de tal modo que se pueda aplicar esta solución una y otra vez, sin repetir cada vez lo mismo”. Esta descripción es válida también para los Patrones de Diseño de la Programación Orientada a Objetos. En los siguientes puntos se analizan algunos de los Patrones de Diseño más utilizados.



8.1.1 Fábrica Abstracta (Abstract Factory)

Una de las operaciones más comunes al programar con objetos es, lógicamente, la creación de los objetos. Sin embargo, esta operación es en sí misma un foco de acoplamiento. Cuando desde un fragmento de código C invocamos la creación de un objeto de la clase A estamos acoplando ese código con el de la clase A. Si posteriormente deseamos cambiar el objeto de clase A por otro de otra clase que cumpla su misma interfaz no podremos hacerlo sin cambiar el código C.

Para evitar este problema se suele delegar la creación de los objetos a otro objeto que se denomina fábrica (Factory). De esta manera desde el código C no creamos el objeto A directamente, sino que se lo pedimos a la clase fábrica. Evidentemente, para evitar el acoplamiento de la fábrica con el código C, la propia fábrica deberá obtenerse por parámetros.



Además, el patrón Fábrica permite ocultar los constructores de las clases que crea, de manera que solo se puedan crear los objetos a través de la fábrica, impidiendo de esta forma su creación de una forma no prevista.

A continuación se presenta un ejemplo en el que el patrón método de fabricación se utiliza para que un sistema gráfico pueda crear diferentes tipos de caracteres. En este caso, la separación entre los objetos fábrica y el sistema gráfico permite añadir nuevos tipos de fuentes y que el sistema gráfico no deba ser modificado.
Existen otros Patrones de Diseño para la creación de objetos. En particular se puede destacar al patrón Constructor (Builder) y al patrón Método de Construcción (Factory Method).

El patrón Constructor es similar al patrón Fábrica Abstracta salvo en que una Fábrica suele crear colecciones de objetos, mientras que un constructor solo crea un tipo de objetos. Por otro lado, el patrón Método de Construcción se diferencia del patrón Fábrica en que son los propios objetos derivados los que crean, mediante un método de construcción, los objetos concretos que se necesitan en cada momento.

Otra alternativa al uso del patrón Fabrica Abstracta consiste en el uso de inyectores de dependencias. Son objetos que se programan o se configuran para que devuelvan familias concretas de productos cuando cualquier clase de la aplicación le solicita cierto tipo de producto. Estas técnicas se apoyan en las características de introspección de Java y pueden ser complementarias al uso de Fábricas Abstractas.

8.1.2 Adaptador o Envoltorio (Adapter o Wrapper)

El patrón Envoltorio se utiliza cuando se desea que una clase utilice otra aunque que no cumple cierta interfaz obligatoria. Por ejemplo, en el diagrama adjunto la clase Cliente solo puede utilizar objetos que cumplan la interfaz Amiga, pero se desea utilizar sobre la clase Extraña. Para ello, se crea la clase Envoltorio, que contiene un objeto de la clase

Extraña pero que implementa la interfaz Amiga. De esta forma, la clase Usuaria utiliza, indirectamente, la clase Extraña.



El cliente accede a la clase extraña utilizando una interfaz que conoce y que envuelve a la clase extraña.

Este patrón se utiliza cuando deseamos almacenar un tipo primitivo de Java en un derivado de Collection. Por ejemplo, supongamos que deseamos almacenar un int en un Vector.

Como los enteros no son elementos de la clase Object es necesario envolverlos en otra clase que contenga el entero y que, al derivar de Object, sí pueda ser insertada en el vector. Por eso, y por otras razones, en Java existen clases como Integer, Float, Boolean o Character que son envoltorios de los tipos primitivos.



En este caso el adaptador es Integer y adapta al tipo primitivo int para que pueda ser usado como un Object.