Escribir imagen a la respuesta del servlet con el mejor rendimiento

Estoy escribiendo una imagen a la respuesta de servlet con el mejor rendimiento. ¿Algún consejo, práctica o experiencia?

Para obtener el mejor rendimiento y eficiencia, no coloque todo el contenido en byte[] . Cada byte come, sí, un byte de la memoria de Java. Imagina 100 usuarios concurrentes que solicitan 10 imágenes de cada 100 KB, eso ya consume 100 MB de memoria de Java.

Obtenga la imagen como un InputStream desde el DB usando ResultSet#getBinaryStream() , envuélvalo en un BufferedInputStream y escríbalo en el OutputStream de la respuesta envuelta en un BufferedOutputStream través de un buffer de byte[] pequeño byte[] .

Suponiendo que selecciona imágenes por la clave de la base de datos como identificador, use esto en su HTML:

  

Cree una clase Servlet que esté mapeada en web.xml en un url-pattern de /images/* e implemente su método doGet() siguiente manera:

 Long imageId = Long.valueOf(request.getPathInfo().substring(1)); // 123 Image image = imageDAO.find(imageId); // Get Image from DB. // Image class is just a Javabean with the following properties: // private String filename; // private Long length; // private InputStream content; response.setHeader("Content-Type", getServletContext().getMimeType(image.getFilename())); response.setHeader("Content-Length", String.valueOf(image.getLength())); response.setHeader("Content-Disposition", "inline; filename=\"" + image.getFilename() + "\""); BufferedInputStream input = null; BufferedOutputStream output = null; try { input = new BufferedInputStream(image.getContent()); output = new BufferedOutputStream(response.getOutputStream()); byte[] buffer = new byte[8192]; for (int length = 0; (length = input.read(buffer)) > 0) { output.write(buffer, 0, length); } } finally { if (output != null) try { output.close(); } catch (IOException logOrIgnore) {} if (input != null) try { input.close(); } catch (IOException logOrIgnore) {} } 

En ImageDAO#find() puede usar ResultSet#getBinaryStream() para obtener la imagen como un InputStream de la base de datos.

puede usar byte del tipo de matriz para la imagen del servlet si está allí en el tipo de base de datos de Blob.

 byte[] image; 

o hay una forma más, pero es un poco complejo. cuando llame a su servlet, antes de eso debe identificar si la llamada es para imagen o si es una llamada normal. si es una llamada normal, puede continuar para llamar a servlet, pero si es una llamada de imagen, no llame a servlet, pero puede almacenar las referencias de imagen en alguna ubicación física en la computadora y recuperar la misma.

Pero este método no funcionará si tiene imágenes en DB, más bien puede tener rutas relativas en DB y luego puede recuperar la imagen desde esa ruta.

Si las imágenes son estáticas, tenga en cuenta que la respuesta más rápida es la que se maneja antes de llegar a usted.

Puedes poner de pie el httpd de Apache frente a tu servidor Tomcat. Puede usar otras variantes de servidores de memoria caché. Hay muchos trucos en esa línea.

Por supuesto, esto supone que su aplicación está escrita donde una URL se correlaciona efectivamente con una imagen de una manera que se almacena fácilmente en caché. Si su aplicación carece de esto, los beneficios son lo suficientemente buenos como para considerar una reestructuración.