De Grav a Hugo

Reconstruyendo este blog como un sitio estático en Cloudflare


Durante años este blog corrió sobre Grav , un CMS flat-file muy agradable. Sin base de datos, solo archivos Markdown, cosa que siempre me gustó. Pero aun así necesita hosting con PHP, actualizaciones y el arreglo ocasional de algún plugin, y me di cuenta de que pasaba más tiempo manteniendo el sitio que escribiendo en él. Así que lo reconstruí como un sitio estático con Hugo . Aquí va el por qué y el cómo.

Por qué mudarse

  • Velocidad. HTML estático servido desde un CDN es de lo más rápido que hay en la web.
  • Costo. El hosting estático es prácticamente gratis.
  • Seguridad. Sin PHP, sin base de datos, nada que parchear ni que hackear.
  • Simplicidad. Desplegar es un git push, nada más.
  • Portabilidad. Son solo Markdown y un puñado de plantillas. Fácil de volver a mover si algún día quiero.

¿Por qué Hugo en concreto? Es un único binario de Go, los builds son ridículamente rápidos, y el soporte multilingüe es de primera, lo cual importa porque este blog está en inglés y español. Además tiene render hooks y un pipeline de assets, que hicieron la migración mucho más limpia.

Mover el contenido

Grav guarda cada página como un archivo Markdown con front matter YAML dentro de user/pages. Hugo usa content/ con page bundles , así que el mapeo fue en su mayoría mecánico:

  • Cada página de Grav se convirtió en un bundle (index.en.md / index.es.md), que también es como Hugo enlaza las traducciones entre sí.
  • El published: false de Grav pasó a ser draft: true en Hugo.
  • El taxonomy: category / tag de Grav pasó a ser categories y tags.
  • Los medios de cada página se movieron al bundle y se referencian desde el front matter images.
Las notas tipo callout de Grav y sus atributos de imagen no mapeaban uno a uno, así que los recreé como shortcodes de Hugo y un render hook de Markdown. Ese render hook además resuelve las rutas relativas de las imágenes hacia el bundle para que los archivos realmente se publiquen.

Búsqueda sin backend

Grav hacía la búsqueda del lado del servidor con un plugin. Un sitio estático no tiene backend, así que me cambié a Pagefind : construye un índice de búsqueda al momento del deploy y corre completamente en el navegador. Es lo que impulsa la búsqueda inline aquí mismo en el blog, sin servidor de por medio.

Hosting en Cloudflare

El sitio pasó de un hosting con PHP a Cloudflare como un Worker de assets estáticos. Todo el pipeline de despliegue es ahora un git push: un build ejecuta Hugo y Pagefind, y luego sube la carpeta public/ al edge.

  • _redirects maneja la redirección de www al dominio raíz.
  • _headers define tiempos de caché largos para fuentes, imágenes y assets con hash.
  • El dominio personalizado y el SSL son automáticos.

Un par de detalles que vale la pena saber

Imágenes: Hugo no publica las imágenes de un bundle a menos que algo las referencie. Un render hook que resuelve cada imagen de Markdown a su page resource arregló de una sola vez tanto la URL como la publicación.
  • Las traducciones se enlazan automáticamente cuando dos archivos comparten un bundle (index.en.md / index.es.md), lo que además alimenta las etiquetas hreflang.
  • La página 404: con defaultContentLanguageInSubdir Hugo solo genera /en/404.html y /es/404.html, así que el build copia una a la raíz del sitio para que el host la sirva en URLs desconocidas.
  • El resaltado de código usa Chroma con estilos basados en clases, lo que me permitió hacerlo consciente del tema para el modo oscuro.

Un look más limpio, y una voz

Ya que estaba en ello, aproveché para pulir el diseño hacia algo más limpio y minimalista, y para apostar por un tema claro/oscuro en condiciones.

También añadí un pequeño botón de Escuchar el post (abajo a la derecha en cualquier artículo). Lee el post en voz alta usando la síntesis de voz del navegador, y es lo bastante listo como para saltarse los bloques de código, las tablas y las imágenes, cambiándolos por un rápido “aquí hay un bloque de código, échale un vistazo en la versión escrita” para que nadie tenga que oír a alguien deletreando XML. Seré honesto: la voz es robótica y un poco horrible. Pero si te cuesta leer, o simplemente hoy te da pereza, debería venir bien. :)

¿Valió la pena?

Totalmente. El sitio es más rápido (puntuaciones de Lighthouse casi perfectas), el hosting es gratis, no hay nada que parchear y publicar es simplemente un commit.

Si tienes un sitio pequeño basado en PHP que usas principalmente para servir contenido, un generador estático como Hugo vale mucho la pena.

Espero que esto ayude.

Si tienes alguna pregunta o hiciste una mudanza parecida, siéntete libre de compartir en los comentarios a continuación.