Java EE y Web 2.0

Mi compañero Luis acaba de pasarme un artículo escrito por un grupo de desarrolladores de IBM y trata sobre la problemática que existe en el mundo Java para desarrollar aplicaciones que implementen el concepto de Web 2.0. Esto responde un poco a la pregunta que se lanzaba en el post ¿Por qué hay tan pocos grandes sitios Web escrito en Java?

La mayoría de estos sitios que se tienen en cuenta en la estadística, implementan el concepto de Web 2.0 y, puesto que Java tiene una serie de carencias para implementar Web 2.0 debido al uso de APIs síncronas, la mayoría de esos sitios están implementados en PHP (esto lo trataremos de demostrar a continuación). Por eso la mayoría de sitios de ocio están programados en PHP u otras tecnologías que no son Java puro( puede que sea Java y Flex, pero nunca con Java como única tecnología).

Principios y cosas asumidas en Java EE

La plataforma Java EE fue creada para desarrollar aplicaciones B2C y B2B, pero en absoluto fue pensado para aplicaciones C2C (que es el concepto que utiliza Web 2.0). Muchas cosas que se dan por sentadas, tanto implícita como explícitamente, en la arquitectura Java EE aparecen reflejadas en las comparativas:

  • El rendimiento de la petición es la característica más importante que afecta al rendimiento desde el punto de vista del cliente.
  • La duración de la transacción es el factor más importante en el rendimiento, y el rendimiento global puede ser mejorado acortando cada transacción.
  • Sólo unos pocos objetos de negocio son afectados por la mayoría de las transacciones.
  • La duración de una transacción está limitada por el rendimiento del servidor de aplicaciones y el EIS (Enterprise Integration System) desplegado en el mismo dominio administrativo.
  • El coste de la comunicación de red (cuando se trabaja con recursos locales) está adecuadamente compensado a través de la agrupación de conexiones (conection pooling).
  • La duración de una transacción puede ser acortada invirtiendo en la configuración de red, hardware y software.
  • Los contenidos y los datos de la aplicación están bajo control del dueño de la aplicación. Sin dependencias de servicios externos, el factor más limitante para proveer de contenido a un cliente es el ancho de banda.

Los principios en los que Java EE está construido:

  • APIs síncronas: Java EE requiere APIs síncronas para muchos propósitos, exceptuando JMS, esto habrá sido más por un tema de usabilidad que de rendiemiento. Una API síncrona es fácil de usar y es adecuada cuando existe una sobrecarga pequeña. De hecho, pueden aparecer múltimple problemas cuando se requiere multithreading, así que, Java EE desaconseja el multithreading incontrolado.
  • Agrupaciones de threads limitadas(Bounded thread pools): Rápidamente se descubrió que el thread es un recurso importante y que el rendimiento del servidor de aplicaciones puede resentirse significativamente si el número de threads supera un límite. Si se asume que las operaciones son cortas, estas operaciones pueden ser distribuidas entre un número limitado de threads para manterner un throughput alto de la request.
  • Agrupaciones de conexiones limitadas(Bounded connection pools): Utilizar una única conexion a la base de datos hace difícil obeter un buen rendimiento de la base de datos. Es posible ejecutar varias operaciones sobre la base de datos en paralelo, pero las conexiones adicionales a la base de datos aceleran la aplicación sólo en un punto. Llegado a un número de conexiones el rendimiento se degrada. Generalmente el número de conexiones es menor que el número de threads disponibles en el pool de threads del servlet. Por ello, los servlets o los EJBs utilizan la conexión y después la devuelven al pool, si la conexión es imposible bloquean el thread actual. Dado que los demás componentes no retienen la conexión mucho el tiempo de espera es corto.
  • Conexiones sujetas a los recursos: Se asume que las aplicaciones utilizarán sólo unos pocos recursos externos que se obtinenen utilizando la interfaz Java Naming and Directory Interface (JNDI). Prácticamente la mayor Java EE API que soporta conexiones a recursos de diferentes EIS es la API para Web services. Otras asumen que los recursos están fijados y que los únicos datos adicionales que se proporcionarán para abrir la conexión son las credenciales del usuario.

Cambios con Web 2.0

Web 2.0 tiene características específicas que hacen difícil al elección de Java EE como implementación. Las aplicaciones utilizan las APIs para acceder a los servicios de otras mucho más que en las típicas aplicaciones de Web 1.0, inclinación por la interacción de tipo consumidor a consumidor (C2C), es decir, el propietario sólo genera una pequeña parte del contenido de la aplicación; la mayor parte es generada por el usuario.

SOA+B2C+Web 2.0 = Latencia muy alta

La aplicaciones Web 2.0 utilizan frecuentemente servicios y feeds que están atados al la API del servicio SOA. Estas aplicaciones necesitan consumir servicios en un contexto B2C. Por ejemplo, una aplicación puede mostrar información sobre las condiciones climáticas, información sobre el tráfico y un mapa de carreteras, obteniendo cada información de un recurso distinto. El tiempo de conseguir cada parte se añade al tiempo global de procesar la petición.

Existen técnicas de cacheo que pueden aliviar la latencia, pero no son aplicables en todas las situaciones. No es práctico e impensable, por ejemplo, cachear resultados de consultas o tráfico de información que se obtine en tiempo real.

Por su propia naturaleza, la invocación de servicios es un proceso lento y con una alta latencia que normalmente coloca sólo una pequeña porción de los recursos de CPU en el cliente y en el servidor. La mayor parte de la duración de la invocación de un servicio se gasta en establecer la conexión y en trasmitir los datos. Por lo tanto, mejorar el rendimiento en el cliente o en el lado del servidor generalmente son sólo una pequeña reducción en la duración de la llamada.

Mayor interactividad

Al habilitar la participación del usuario, Web 2.0 la aplicación tiene un mayor número de peticiones al servidor por usuario. Esto es verdad por varias razones:

  • Hay un mayor número de eventos relevantes ya que la mayoría de los eventos están causados por acciones de otros clientes, y los clientes tiene una capacidad mucho mayor para generar eventos. Estos eventos naturalmente causan un mayor uso activo de las aplicaciones Web por parte de los clientes.
  • Las aplicaciones proveen un número mucho mayor de casos de uso a los clientes. Ahora, los clientes pueden establecer contactos activamente con otros clientes por medio de foros, chats,etc, causando un mayor tráfico de carga.
  • Las aplicaciones de hoy en día utilizan Ajax cada vez más para mejorar la experiencia del usuario. Un página que utilice Ajax tiene un menor tiempo de carga que una que no lo utilice, porque la página consiste en contenido estático, scripts y un número de peticiones al servidor. Después de ser cargada, un página Ajax crea a menudo varias peiticiones más cortas al servidor.

Estos factores causan generalmente una gran cantidad de tráfico para el servidor y un gran número de peticiones, en comparación con una aplicación Web 1.0. Durante las grandes cargas, el tráfico es difícil de controlar.

Mayor contenido

Las aplicaciones Web 2.0 tienen un mayor cantidad de contenido y de mayor peso que las aplicaciones Web 1.0.

En el mundo de las aplicaciones Web 1.0 el contenido de las aplicaciones era publicado en el Web site de la empresa después de que la empresa lo aprobara. La empresa tenía el control absoluto sobre el contenido de lo que allí había desplegado, si algo daba algún problema se optimizaba para que no hubiera problemas. Una gran parte de las aplicaciones Web 2.0 es generada por el usuario y por las comunidades. Las empresas sólo proveen la aplicación y las herramientas para generar contenido. El contenido aumenta en tamaño debido al uso de imágenes, audio y vídeo.

Conexiones Persistentes

Establecer una nueva conexión entre cliente y servidor lleva un tiempo significativo. Es mucho más eficiente establecer la comunicación entre cliente/servidor una vez y reutilizarla. Las conexiones persistentes son también útiles para enviarle notificaciones al cliente. Pero en las aplicaciones Web 2.0 generalmente están tras cortafuegos, y generalmente suele ser imposible establecer una conexión directa enter cliente/servidor.

Una aplicación Ajax necisita enviar peticiones para votar por eventos específicos. Para reducir el número de peticiones de voto, algunas aplicaciones Ajax utilizan el patrón Comet: El servidor está diseñado para esperar hasta que ocurra un evento antes de mandar una respuesta, mientras mantenga la conexión abierta.

Alto riesgo del efecto Slashdot

Las aplicaciones Web 2.0 pueden llegar a gran cantidad de personas y hacen algunos sitios Web más vulnerables al efecto “Slashdot”, es decir, un tremendo pico de tráfico que ocurre cuando un sito es mencionado en un blog popular, nuevo sitio, o red social. Todas la Webs deberían estar preparadas para manejar tráfico varios órdenes de magnitud superior al normal. Y lo que es más importante al mismo tiempo deberían ser capaces de perder calidad de manera elegante bajo una sobrecarga fuerte de tráfico.

Problemas de latencia

La latencia de las operaciones afecta más a las aplicaciones Java EE que el throughput de cada operación. Incluso si el servico de una aplicación puede manegar un gran volumen de operaciones, tiene la misma latencia e incluso puede incrementarse. El conjunto de las aplicaciones Java EE no manejan bien está situación porque viola la suposición de que la latencia está implícita en el diseño de estas APIs.

Servir una página grande de un foro o de un blog conlleva procesar el thread cuando se usa una API síncrona. La página puede tardar un segundo en ser servida, si se tienen 100 threads en un pool, es imposible servir 100 páginas por segundo, una tasa inaceptable. El aumentar el número de threads en el pool tiene un beneficio limitado porque el rendimiento del servidor de aplicaciones empieza a degradarse a medida que se aumenta el número de threads en el pool.

La arquitectura Java EE no puede aprovecharse de los protocolos de mensajería, como SIP, BEEP y XMPP porque la API síncrona de Java EE utiliza un único thread continuamente. Dado que los servidores utilizan pools con ún número limitado de threads, el contínuo uso de un thread impide al servidor de aplicaciones,cuando se están utilizando estos procotolos, atender otras peticiones mientras envía o recibe un mensaje. Hay que tener en cuenta, que los mensajes enviados con estos protocolos no tienen porque ser cortos, y que generarlos puede conllevar el acceder a recursos externos que pertenezcan a otras empresas u organizaciones. También los protocolos de transporte como BEEP y Stram Control Transmission Protocol (SCTP) pueden tener varias conexiones lógicas simultáneamente sobre la misma conexión TCP/IP, lo cual hace que el asunto del manejo de threads sea más delicado.

Para implementar aplicaciones que utilicen streaming, directamente se han abandonado los patrones típicos en Java EE y sus APIs. Como resultado los servidores de aplicaciones Java EE raramente se utilizan para ejecutar aplicaciones P2P o en las que se realice video streaming. A menudo se desarrollan componentes “ad hoc” para manejar estos protocolos y generalmente utilizan conectores Java Connector Arquitecture (JCA) para implementar la lógica asícrona de manera propietaria. Como se verá más adelante, una nueva generación de servlets que soportan algunas interfaces no estádares han surgido para implementar el patrón Comet.

Por último, otra de las cosas asumidas en los principio fundamentales de Java EE es que la inversión en la infrastructura de red puede acortar la duración de la transacción. En el caso de los feeds de vídeo, aunque se aumente la velocidad de la infraestructura de red no afectará a la duración de la petición al servidor porque el vídeo es enviado al cliente mientras está siendo generado. Las mejoras sobre la infraestructura de red sólo incrementarían el número de vídeos a habilibitar a los clientes y facilitarían el poder realizar streaming a resoluciones más altas.

La solución asíncrona

Una posible para solucionar todos los problemas que hemos comentado anteriormente, es tener en cuenta la latencia de la aplicación en el diseño y optar por una implementación asíncrona y orientada a eventos.

Una ventaja del diseño asíncrono y orientado a eventos es que las múltiples operaciones que esperan por servicios externos pueden ser ejecutadas en paralelo si no existe ninguna dependencia de datos entre ellas. Además el diseño asíncrono y orientado a eventos escala mucho mejor que el diseño síncrono tradicional, incluso si no hay operaciones que se ejecuten en paralelo.

Estudio empírico

Llegados a este punto los chicos de IBM hacen un estudio empírico en el que tienen en cuenta los aspectos más relevante de una aplicación Web 2.0: El tiempo de parseo de la información de una petición, El tiempo de realizar una transacción a una base de datos local, el tiempo de procesado de la transacción local y el tiempo de preparación para una llamada a un servicio remoto, el tiempo de la llamada a un servicio remoto y la creación de la respuesta.

Estos chicos plantean varias situaciones con varios threads en el que comparan la solución asíncrona y con la síncrona y los resultados son abrumadores. Pese a tener más threads en el pool la solución síncrona se pasa esperando a que terminen las operaciones remotas mucho tiempo, frente a la solución asíncrona que una vez conseguida la primera conexión genera una respuesta a un intervalo regular. En el peor de los casos la ganancia de tiempo es de un 40% de la solución asíncrona con respecto a la síncrona, pero en el mejor de los casos es de un 225%, vamos que los datos hablan y hay poco que discutir al respecto.

Para el que esté interesado en este punto, le aconsejo que se mire el artículo original, a mí me parece que sería extender en demasía este post, pero no puedo menos que aconsejar su lectura porque es muy interesante.

Implementaciones

El artículo original da nombres y explica en detalle algunas de las tecnologías, todas ellas en fase de prototipo y no probadas en entornos reales, que se han desarrollado para programar aplicaciones de manera asíncrona en Java EE. Se han implementado soluciones de propósito general y soluciones que reimplementan los servlets de manera asíncrona para problemas concretos, os dejo un listado con las soluciones el que quiera indagar ya sabéis podéis visitar el artículo original.

Soluciones de propósito general

  • Staged event-driven architecture (SEDA)
  • E programing language
  • AsyncObjects framework
  • Waterken’s ref_send
  • Frugal Mobile Objects
  • Scala Actors

APIs específicas para soluciones específicas

  • JSR 203 (NIO.2)
  • Glassfish Grizzly NIO
  • Jetty 6 continuations
  • Apache Tomcat 6 Comet API
  • JAX WS 2.0 and Apache Axis3 Asynchronus Web Service Client API

Conclusion

El mundo Java EE tiene una serie de carencias para ejecutar aplicaciones Web 2.0 debido al uso de APIs síncronas que hacen que las latencias sean inaceptables para el usuario. Por otro lado, no hay nada estándar en el mundo Java EE con lo que la gente se ha lanzado a la aventura de la programación asíncrona y hoy por hoy no hay nada lo suficientemente probado como para arriesgarse a ponerlo en producción.

Por otro lado, soluciones como PHP, disponen del modelo ejecución “share nothing” propio del servidor Apache, con lo que no hay compartición de datos entre las peticiones, ofreciendo un modelo de ejecución “asíncrono”, lo cual ha permitido la proliferación de aplicaciones Web 2.0 en esta tecnología. Esta vez PHP se ha adelantado y ha pegado primero.

Os dejo el link del artículo original para que el quiera indagar más lo haga:

http://www.ibm.com/developerworks/web/library/wa-aj-web2jee/?ca=dgr-

4 Comentarios

  • 1. santi  |  Noviembre 23rd, 2007 at 11:20 am

    Me dices que no hay grandes sitios Web 2.0 hechos con Java? Mira algunas de las aplicaciones de Google. Y mirate la API Google Web Toolkit (GWT), ya me contaras si te da la posibilidad de hacer aplicaciones con peticiones asincronas… (no es parte de J2EE pero usa servlets en el servidor y solo Java en el cliente, aqui lo traduce a javascript) Me parece que los de IBM no han hecho un anlisis tan exhaustivo…

  • 2. Luis Artola  |  Noviembre 23rd, 2007 at 1:17 pm

    Hola Santi,
    GWT, si no me equivoco, es un Toolkit para hacer aplicaciones con AJAX. AJAX permite hacer peticiones al servidor sin recargar la página… y a eso se le llama hacer peticiones asíncronas. ¡Pero asíncronas para la navegación!

    No tiene nada que ver con la forma en la que los servidores aceptan peticiones…

    Respecto a las aplicaciones google web 2.0 hechas en Java: ¿Cuales son? Digo para echarles un vistazo …

    un saludo!

  • 3. Raúl Vicente  |  Noviembre 23rd, 2007 at 2:18 pm

    Luis tiene razón, pero a lo que se refieren los de IBM es que todas las implementaciones que hay, para lo que dice Luis, no para hacer aplicaciones Ajax, son soluciones propietarias que o bien valen para problemas concretos, o bien si son soluciones generales a parte de estar en fase prototípica no siguen ningún tipo de estándar porque actualmente no lo hay, así que una aplicación que se implemente usando eso y que tenga esperanzas de tener un ciclo de vida relativamente largo está vendida.

    Un saludo y gracias a los 2.

  • 4. luis  |  Mayo 22nd, 2009 at 11:24 am

    hola raul! soy un recien titulado que esta de becario en una empresa aprendiendo iceface paraposteriormente desarrollar aplicaciones woodstock-icefaces.
    El motivo de mi correo es que si bien voy avanzando bastante, tengo un problemilla que seguro habras resuelto y me solucionarias un problema importante.
    No he podido configurar un proyecto en el que coexistan una pagina woodstock y otra de icefaces(la coexistencia a nivel de pagina no la vamos a usar en mi empresa).
    Asi si pudiera mandarme un proyectito con el que tu empezaras a cacharrear que tenga una pagina woodstock y otra icefaces no sabes cuanto te lo agradeceria. Muchisimas gracias!!

    mi correo es luisoarenas@gmail.com

Comenta el articulo:

Requerido

Requerido,