Configura el comportamiento del almacenamiento en caché de HTTP

En este codelab, se muestra cómo cambiar los encabezados de almacenamiento en caché de HTTP que devuelve un servidor web basado en Node.js que ejecuta el framework de entrega Express. También se mostrará cómo confirmar que el comportamiento de almacenamiento en caché que esperas se aplica realmente, con el panel Network de las Herramientas para desarrolladores de Chrome.

Familiarízate con el proyecto de ejemplo

Estos son los archivos clave con los que trabajarás en el proyecto de ejemplo:

  • server.js contiene el código de Node.js que entrega el contenido de la app web. Usa Express para controlar las solicitudes y respuestas HTTP. En particular, express.static() se usa para entregar todos los archivos locales en el directorio público, por lo que la serve-static documentación será útil.
  • public/index.html es el código HTML de la app web. Al igual que la mayoría de los archivos HTML, no contiene información de versiones como parte de su URL.
  • public/app.15261a07.js y public/style.391484cf.css son los recursos de JavaScript y CSS de la app web. Cada uno de estos archivos contiene un hash en sus URLs, que corresponde a su contenido. El elemento index.html es responsable de hacer un seguimiento de qué URL específica con versión se debe cargar.

Configura encabezados de almacenamiento en caché para nuestro código HTML

Cuando respondas a solicitudes de URLs que no contengan información de versiones, asegúrate de agregar Cache-Control: no-cache a tus mensajes de respuesta. Además, se recomienda configurar uno de los dos encabezados de respuesta adicionales: Last-Modified o ETag. El index.html entra en esta categoría. Puedes dividirlo en dos pasos.

En primer lugar, los encabezados Last-Modified y ETag se controlan con las opciones de configuración etag y lastModified. En realidad, ambas opciones se establecen de forma predeterminada en true para todas las respuestas HTTP, por lo que, en esta configuración actual, no tienes que habilitar la opción para obtener ese comportamiento. Sin embargo, puedes ser explícito en tu configuración.

En segundo lugar, debes poder agregar el encabezado Cache-Control: no-cache, pero solo para tus documentos HTML (index.html, en este caso). La forma más fácil de establecer este encabezado de forma condicional es escribir un setHeaders function personalizado y, dentro de él, verificar si la solicitud entrante es para un documento HTML.

  • Haz clic en Remix to Edit para que el proyecto se pueda editar.

La configuración de entrega estática en server.js comienza de la siguiente manera:

app.use(express.static('public'));
  • Realiza los cambios descritos anteriormente y deberías obtener algo similar a lo siguiente:
app.use(express.static('public', {
  etag: true, // Just being explicit about the default.
  lastModified: true,  // Just being explicit about the default.
  setHeaders: (res, path) => {
    if (path.endsWith('.html')) {
      // All of the project's HTML files end in .html
      res.setHeader('Cache-Control', 'no-cache');
    }
  },
}));

Configura encabezados de almacenamiento en caché para las URLs con versiones

Cuando respondas a solicitudes de URLs que contengan información de "huella digital" o de versiones, y cuyo contenido nunca deba cambiar, agrega Cache-Control: max-age=31536000 a tus respuestas. app.15261a07.js y style.391484cf.css entran en esta categoría.

A partir del objeto setHeaders function que se usó en el último paso, puedes agregar lógica adicional para verificar si una solicitud determinada es para una URL con versión y, si es así, agregar el encabezado Cache-Control: max-age=31536000.

La forma más sólida de hacerlo es usar una expresión regular para ver si el activo solicitado coincide con un patrón específico en el que sabes que se encuentran los hashes. En el caso de este proyecto de muestra, siempre son ocho caracteres del conjunto de dígitos del 0 al 9 y las letras minúsculas de la a a la f (es decir, caracteres hexadecimales). El hash siempre está separado por un carácter . a cada lado.

Una expresión regular que coincide con esas reglas generales se puede expresar como new RegExp('\\.[0-9a-f]{8}\\.').

  • Modifica la función setHeaders para que se vea de la siguiente manera:
app.use(express.static('public', {
  etag: true, // Just being explicit about the default.
  lastModified: true,  // Just being explicit about the default.
  setHeaders: (res, path) => {
    const hashRegExp = new RegExp('\\.[0-9a-f]{8}\\.');

    if (path.endsWith('.html')) {
      // All of the project's HTML files end in .html
      res.setHeader('Cache-Control', 'no-cache');
    } else if (hashRegExp.test(path)) {
      // If the RegExp matched, then we have a versioned URL.
      res.setHeader('Cache-Control', 'max-age=31536000');
    }
  },
}));

Confirma el nuevo comportamiento con las Herramientas para desarrolladores

Con las modificaciones en el servidor de archivos estáticos, puedes verificar que se establezcan los encabezados correctos. Para ello, obtén una vista previa de la app activa con el panel Network de Herramientas para desarrolladores abierto.

  • Personaliza las columnas que se muestran en el panel Network para incluir la información más relevante. Para ello, haz clic con el botón derecho en el encabezado de la columna:

Configuración del panel Network de Herramientas para desarrolladores

Aquí, las columnas a las que debes prestar atención son Name, Status, Cache-Control, ETag y Last-Modified.

  • Con las Herramientas para desarrolladores abiertas en el panel de red, actualiza la página.

Después de que se cargue la página, deberías ver entradas en el panel Network similares a las siguientes:

Columnas del panel de red

La primera fila es para el documento HTML al que navegaste. Se entrega correctamente con Cache-Control: no-cache. El estado de la respuesta HTTP para esa solicitud es 304. Esto significa que el navegador sabía que no debía usar el HTML almacenado en caché de inmediato, sino que realizó una solicitud HTTP al servidor web, usando la información de Last-Modified y ETag para ver si había alguna actualización del HTML que ya tenía en su caché. La respuesta HTTP 304 indica que no hay HTML actualizado.

Las siguientes dos filas son para los recursos de JavaScript y CSS con versiones. Deberías ver que se entregan con Cache-Control: max-age=31536000 y que el estado HTTP de cada uno es 200. Debido a la configuración utilizada, no se realiza ninguna solicitud real al servidor de Node.js, y hacer clic en la entrada te mostrará detalles adicionales, incluido que la respuesta provino "(de la caché de disco)".

Un estado de respuesta de red 200.

Los valores reales de las columnas ETag y Last-Modified no son tan importantes. Lo importante es confirmar que se establezcan.

Resumen

Después de completar los pasos de este codelab, ya sabes cómo configurar los encabezados de respuesta HTTP en un servidor web basado en Node.js con Express para un uso óptimo de la caché HTTP. También tienes los pasos que necesitas para confirmar que se está usando el comportamiento de almacenamiento en caché esperado a través del panel Network en las Herramientas para desarrolladores de Chrome.