
¿Sabía que una tienda online puede perder hasta un 7% de conversiones por cada segundo extra de carga? Si PageSpeed muestra fallos o la web se ralentiza tras activar un plugin, migrar a un CDN o cambiar servidor, lo más habitual es una configuración de TTL inconsistente que provoca misses, peticiones innecesarias y errores en recursos estáticos.
Caché del navegador y headers: configurar Cache-Control, Expires y ETag reduce la carga del servidor y mejora Core Web Vitals; en WordPress se aplica desde servidor (Apache/Nginx), CDN (Cloudflare/S3/Fastly) o plugins de caché.
A continuación se presentan ejemplos para Apache y Nginx, ejemplos claros de TTL recomendados por tipo de recurso, estrategias prácticas de invalidación (versionado vs purge) y comandos curl/DevTools reproducibles para verificar los efectos. (He sustituido la promesa de una 'tabla' por 'ejemplos claros de TTL' para reflejar el contenido real y evitar la expectativa de una tabla que no existe.)
Índice
Anuncio
Resumen del proceso: pasos rápidos para aplicar ahora
- Comprobar headers actuales con curl y DevTools. 2. Elegir la "fuente de verdad" (servidor, CDN o plugin). 3. Aplicar TTL corto en HTML y TTL largo en assets versionados. 4. Implementar versionado para evitar purges masivos. 5. Verificar impacto en Core Web Vitals con Lighthouse.
¿Qué se consigue en minutos?
En 10–30 minutos se puede identificar la configuración actual con curl y DevTools. En 1–3 horas se aplican cambios básicos en .htaccess o Nginx. En 1 deploy con versionado se logra TTL largos seguros para assets.
Herramientas que se usan ahora
Curl, Chrome DevTools, Lighthouse y la API de tu CDN permiten verificar cambios de forma reproducible. Un solo comando curl muestra Cache-Control, Expires, ETag y Vary.

Paso 1: identificar headers y definir la fuente de verdad
El primer paso es saber qué respuesta recibe el navegador y quién la genera. Hazlo con curl y con una lectura del tráfico en DevTools antes de cambiar nada.
¿Cómo comprobar headers con curl?
Usar curl -I -L https://tu-dominio.com devuelve las cabeceras principales en segundos. Para forzar petición limpia: curl -H "Cache-Control: no-cache" -I https://tu-dominio.com. Guardar resultados facilita comparar antes y después.
¿Quién tiene prioridad: servidor, CDN o plugin?
La prioridad depende del flujo: si existe CDN en front, el edge puede reescribir headers del origen. Si un plugin añade headers y el servidor ya los envía, el último que modifique la respuesta será el efectivo. El error más frecuente en este punto es no documentar la fuente de verdad y aplicar cambios en varios sitios.
Anuncio
Paso 2: cambiar headers en apache y nginx
Modificar headers en el servidor garantiza control directo cuando el CDN respeta el origen. A continuación hay ejemplos listos para copiar en Apache (.htaccess) y Nginx.
Ejemplo para apache
Inserta estas líneas dentro de la configuración del sitio o en .htaccess cuando mod_expires y mod_headers estén activos.
<IfModule mod_expires.c>
ExpiresActive On
ExpiresByType text/html "access plus 60 seconds"
ExpiresByType text/css "access plus 1 year"
ExpiresByType application/javascript "access plus 1 year"
ExpiresByType image/* "access plus 30 days"
</IfModule>
<IfModule mod_headers.c>
Header always set Cache-Control "public, max-age=31536000, immutable" env=HAS_HASH
Header always set Cache-Control "no-cache, must-revalidate" env=!HAS_HASH
FileETag None
</IfModule>
Ejemplo para nginx
Añade estos bloques dentro del server o en un include. La directiva always= on asegura que add_header aplique con errores 4xx/5xx.
location ~* /.(css|js)$ {
add_header Cache-Control "public, max-age=31536000, immutable" always;
access_log off;
}
location ~* /.(png|jpg|jpeg|gif|webp|svg)$ {
add_header Cache-Control "public, max-age=2592000" always;
access_log off;
}
location / {
add_header Cache-Control "no-cache, must-revalidate" always;
}
etag off;
Cache-Control merece una explicación práctica porque cada directiva cambia el comportamiento de la caché del navegador y del CDN. max-age=<segundos> fija un TTL absoluto en el cliente; para assets versionados se usa max-age=31536000, immutable, public (un año) para que el navegador no vuelva a validar. s-maxage funciona igual pero es prioritaria en caches compartidos (CDN/edge); úsala cuando quieras que el edge tenga una vida distinta al navegador. no- obliga a revalidar en cada petición (se negocia con If-None-Match/If-Modified-Since), mientras que no-store impide almacenamiento en cualquier caché (útil para datos sensibles). must-revalidate exige revalidación cuando el recurso expira, y immutable es óptimo para assets con hash en el filename: el navegador asume que no cambiarán y evita revalidaciones.
Finalmente, stale-while-revalidate y stale-if-error son útiles en el edge para servir contenido ligeramente obsoleto mientras se revalida o cuando el origen falla, mejorando TTFB y evitando picos en Core Web Vitals; aplícalos con prudencia en recursos no críticos.
Paso 3: CDNs, plugins y estrategias de invalidación
Un CDN puede mejorar la latencia, pero también puede ocultar un problema de headers mal aplicados. Mapear cómo el CDN trata los headers evita sorpresas durante deploys.
Cloudflare, Fastly y CloudFront
Cloudflare permite Page Rules o Transform Rules para sobrescribir Cache-Control y Edge TTL. Fastly admite VCL y surrogate-keys para purges selectivos. CloudFront respeta metadata de S3 salvo que un Behavior lo sobrescriba. RFC 7234 (IETF, 2014) sigue siendo la referencia para entender estos comportamientos RFC 7234.
Plugins en WordPress
Plugins como WP Rocket, W3 Total Cache o WP Super Cache generan cabeceras a nivel de aplicación. El error más visto es asumir que el plugin vence al CDN cuando el CDN está en front. Verificar con curl evita confiar a ciegas en la interfaz del plugin.
Tabla comparativa de CDNs
| CDN | Control sobre headers | Purge granulado | Ideal para |
|---|---|---|---|
| Cloudflare | Alto (Page Rules, Workers) | URL, tag; API sencilla | Sitios generales y tiendas pequeñas |
| Fastly | Muy alto (VCL) | Surrogate-keys, purges selectivos | Plataformas con deploys frecuentes |
| CloudFront | Medio (Behaviors) | Invalidación por path, coste según volumen | Integración con S3 y entornos AWS |
Flujo de decisión
Headers origin
Edge TTL y purges
Al usar un CDN hay que mapear explícitamente qué headers vienen del origen y cuáles puede sobrescribir el edge.
- En S3, por ejemplo, setea metadata
Cache-Controlal subir objetos:aws s3 cp app.js s3://mi-bucket/ --acl public-read --cache-control "public, max-age=31536000" --content-type "application/javascript". En CloudFront, habilita que respete los headers del origen (Origin Cache Control) o define un Behavior con TTLs concretos. - En Cloudflare puedes crear Page Rules o usar Workers para forzar
Edge Cache TTLo reescribirCache-Control. Con Fastly es habitual enviar desde el origenSurrogate-Key: products-1234ySurrogate-Control: max-age=31536000. - Fastly puede purgar por
surrogate-keysin invalidar todo.
Estas prácticas garantizan que la cabecera que ve el navegador (Cache-Control/Expires/Surrogate-Control) sea la esperada y que el TTL en el edge y en el cliente estén alineados con tu estrategia de versionado de assets.
Paso 4: invalidación y versionado de assets
La forma más segura de servir TTL largos es renombrar archivos con hash y mantener purges solo para lo urgente. Esto reduce dependencias del CDN y evita invalidaciones masivas.
Cache-busting con hash en filename
Integrar hashes en el pipeline de build (Webpack, gulp) y usar wp_enqueue_script con version en WordPress asegura que el navegador pida el recurso nuevo cuando cambie. Esto funciona bien en teoría, pero en la práctica requiere disciplina en el flujo de deploy.
Purges por API y surrogate-keys
Usar purges por tag o surrogate-key permite invalidar solo lo necesario. Un caso habitual: tras actualizar un CSS global, purgar por tag evita purgar imágenes y reduce latencia de propagación.
El siguiente párrafo resume una recomendación clara: usar versionado de archivos para evitar purges masivas funciona bien, excepto cuando el CMS genera URLs sin incorporar versiones; en ese caso conviene habilitar purges selectivos por API y planificar deploys durante ventanas con menor tráfico.
Las invalidaciones y el cache-busting requieren ejemplos prácticos para ser operativas. Para Cloudflare puedes purgar por URL o por lista vía API: curl -X POST "https://api.cloudflare.com/client/v4/zones/<ZONE_ID>/purge_cache" -H "X-Auth-Email: tu@correo" -H "X-Auth-Key: <API_KEY>" -H "Content-Type: application/json" --data '{"files":["https://tu-dominio.com/css/app.css"]}'. Para CloudFront la invalidación desde CLI es aws cloudfront create-invalidation --distribution-id XXXXXX --paths "/css/*". Fastly soporta purge por surrogate-key con su API o desde VCL; enviando Surrogate-Key: producto-42 desde el origen permite purgar solo ese grupo. Para debug, usa curl para probar revalidaciones: curl -I -H "If-None-Match: /"ETAG/"" https://tu-dominio.com/archivo.js debería devolver 304 si la ETag coincide; con If-Modified-Since pruebas Last-Modified.
Revisa además Age (tiempo en edge) y Vary para entender hits/misses. Estos comandos permiten validar purges y confirmar que el versionado de assets y las purgas son efectivas antes de un deploy masivo.
Anuncio
Errores que arruinan el resultado y cómo evitarlos
Aplicar TTL largo al HTML sin versionado causa problemas de contenido obsoleto y tickets de soporte. Evitar este error es la acción más rentable.
Errores frecuentes al configurar headers
No comprobar la combinación servidor-CDN-plugin y asumir que el plugin vence al CDN. Generar ETags que cambian en cada deploy al incluir inode o timestamp. Usar la misma regla para todos los recursos.
ETag vs Last-Modified
ETags generadas automáticamente pueden incluir datos del sistema que cambian en cada deploy, lo que provoca misses y peticiones 200 frecuentes. La mayoría de guías dicen que ETag siempre ayuda; lo que no mencionan es que ETags basadas en inode anulan la cache entre servidores o después de sincronizaciones.
Cómo corregir ETag problemáticos
En Apache usar FileETag None o limitar a MTime. En Nginx usar etag off y confiar en Last-Modified o en ETag manejados por el build. Probar con curl antes y después confirma que la solución evita 200 innecesarios.
Cuándo no funciona este método y alternativas
Si se prefiere, existe la opción de contratar una auditoría técnica de headers y rendimiento para revisar servidor, CDN y plugin antes de aplicar cambios en producción.
Preguntas frecuentes
¿Cómo comprobar si mi CDN respeta los headers de origen?
Usar curl con la URL directa al origen y con la URL pública del CDN. Comparar Cache-Control, Expires y ETag entre ambas respuestas. Si el edge reescribe, la cabecera mostrada por el dominio público reflejará el cambio.
¿Puedo poner TTL largos en WooCommerce sin romper el sitio?
No es recomendable cachear páginas con carrito o checkout. Mantener TTL corto en HTML de páginas transaccionales y cachear elementos estáticos del frontend. Usar fragment caching o AJAX para partes dinámicas evita problemas.
¿Qué pruebas ejecutar para ver impacto en Core Web Vitals?
Ejecutar Lighthouse o PageSpeed antes y después de cambios en headers. Comparar LCP, FCP y TTFB. Registrar resultados y repetir pruebas en horarios distintos para eliminar ruido de red.
¿Cómo automatizo versionado en WordPress?
Añadir hash en el pipeline de build y pasar la versión a wp_enqueue_script/style. Si no hay pipeline, usar plugins que añaden query string con versión basada en tiempo de deploy, evitando hacerlo por cada carga.
¿Qué ocurre con las cabeceras y la normativa RGPD?
Las cabeceras por sí solas no violan RGPD; el riesgo viene de cachear respuestas con datos personales. Evitar cachear páginas que incluyan información personal o autentificada. Aplicar Vary y no-cache donde proceda.
¿Es mejor usar ETag o Last-Modified?
Last-Modified suele ser más estable si los ficheros no cambian de inode. ETag puede ser eficaz si se controla su generación. Si el servidor genera ETags que cambian con cada deploy, es preferible desactivarlas y usar Last-Modified.
Anuncio
Síntesis con recomendación accionable
Configurar la caché del navegador y los headers reduce bytes transferidos y mejora métricas de experiencia. Definir una fuente de verdad (origen o CDN), aplicar TTL corto a HTML y TTL largo a assets versionados, y usar purges selectivos o versionado minimiza riesgos. Implementar cambios en staging, verificar con curl y Lighthouse, y programar deploys controlados para reducir impacto.
- Por qué tu caching rompe la performance multilingüe
- Reduce LCP y costes con CDN que genera imágenes al vuelo
Josu Barrios
Somos especialistas en mantenimiento WordPress para empresas, profesionales y tiendas online. Contamos con experiencia en seguridad web, optimización de rendimiento, actualizaciones, copias de seguridad y resolución de incidencias técnicas, ayudando a que cada sitio funcione de forma rápida, estable y protegida. Nuestro enfoque combina soporte técnico profesional, buenas prácticas de seguridad y seguimiento continuo para ofrecer un servicio fiable, transparente y orientado a resultados reales.