Cloudflare rehace el module registry de Workers para Node.js

Por qué Cloudflare reescribió el corazón de Workers

Cloudflare reescribió el module registry de Cloudflare Workers dentro de workerd, el runtime open source sobre el que corre su plataforma serverless, para alinearlo con las reglas de Node.js y dejar de tratarlas como un caso especial. El cambio llega tras dos años añadiendo APIs de Node.js al runtime y después de que esas APIs se habiliten por defecto, lo que permite desplegar hoy apps Node enteras en Workers con paquetes de hasta 64 MiB en todos los planes, según explica el equipo de Cloudflare en su blog.

Hasta ahora, el module registry resolvía los specifiers como rutas de filesystem en vez de URLs. Esa diferencia,看似 menor, bloqueaba cosas que cualquier desarrollador de Node da por sentadas: import.meta.url, resolución de relativos igual que new URL(), soporte decente de protocolos como node: y cloudflare:, y la regla clásica de los navegadores en la que ?query y #fragment cuentan como módulos distintos.


Qué cambia concretamente para tu código

El nuevo registry se activa con el flag de compatibilidad new_module_registry:

👥 ¿Quieres ir más allá de la noticia?

En nuestra comunidad discutimos las tendencias, compartimos oportunidades y nos ayudamos entre emprendedores. Sin humo, solo acción.

👥 Unirme a la comunidad
{
  "compatibility_flags": ["new_module_registry"]
}

Al activarlo, los Workers ya soportan de forma nativa los puntos clave que estaban pendientes:

  • import.meta.url, import.meta.main e import.meta.resolve() funcionan como en Node y en el navegador.
  • Los specifiers se parsean y resuelven como URLs reales, con soporte de query strings y fragments. Importar ./counter.js?a y ./counter.js?b devuelve dos instancias distintas del mismo módulo, cada una con su propio estado top-level. Reimportar el mismo specifier devuelve la misma instancia, así que no es una forma de forzar re-evaluación, pero sí respeta la regla de module-identity de los navegadores.
  • Los built-ins node: siempre resuelven al mismo módulo, sin importar cómo los importes.
  • Los import attributes se validan: with { type: 'json' } se acepta, type: 'text' se rechaza con un error específico por estar aún en proposal, y cualquier clave distinta de type es un error duro en vez de ignorarse silenciosamente.
  • require(esm) sigue las reglas de Node: si el ESM expone un export llamado 'module.exports', devuelve eso; si no, devuelve el namespace object. La salvedad importante es el caso ERR_REQUIRE_ASYNC_MODULE: si el módulo (o algo en su grafo) tiene top-level await, require() falla. La respuesta es import() para todo lo async.
  • Los errores son consistentes entre import, import() y require(): «Module not found» es Error plano, los specifiers que no parsean son TypeError (igual que ERR_INVALID_MODULE_SPECIFIER en Node), y las dependencias circulares que V8 no puede desenrollar nunca son TypeError. Eso permite construir loaders o retry wrappers que ramifican por clase de error sin importar quién disparó el fallo.
  • Compilación perezosa: el módulo se compila solo cuando se importa por primera vez (estática o dinámicamente), y los isolates V8 de un mismo Worker comparten caché, así que el mismo source deja de compilarse N veces.

Por qué importa: alinearse con Vite 8 y el futuro del bundling

El cambio tiene una derivada importante para el ecosistema de tooling. Cloudflare integra el plugin oficial de Vite y, como explica el blog, Vite 8 ya viene con Rolldown, el bundler Rust-based que unifica desarrollo y producción. InfoQ documentó en mayo de 2026 que Vite 8 entrega entre 10× y 30× más velocidad de build frente a la config anterior con esbuild y Rollup, con casos como Linear pasando de 46 s a 6 s o Ramp reduciendo su build un 57 %.

El nodo relevante para founders: el nuevo registry permite que bundlers como Rolldown hagan menos transformaciones y deleguen más en el runtime la resolución de módulos. Eso reduce el código que se reescribe, baja la superficie de bugs por transformaciones ad-hoc de import/require(), y abre la puerta a --no-bundle o a subir el grafo de módulos tal cual lo escribiste.

Además del límite de 64 MiB sin tope de compressed size, el otro punto clave que libera casos de uso reales es que Cloudflare eliminó la restricción sobre el tamaño del bundle comprimido en todos los planes, lo que quita el dolor de cabeza clásico de Workers para apps Node con dependencias pesadas.


Cómo probarlo y dónde reportar bugs

El flag new_module_registry no tiene default-on date todavía, así que ni Workers viejos ni nuevos se van a actualizar solos: hay que ponerlo a mano en la configuración. La documentación técnica profunda de cómo interactúa el nuevo registry con las APIs de módulos de V8 ya está mergeada en el repositorio open source de workerd, así que sirve como referencia si vas a tocar bundling interno.

El equipo abrió la invitación a reportar cualquier regresión en el repo de workerd en GitHub; las nuevas APIs y cambios de comportamiento están todos descritos en la documentación oficial. Para activar el flag en proyectos existentes basta con añadir la línea en el wrangler.toml o en el objeto compatibility_flags del JSON de configuración.


¿Qué significa esto para tu startup?

Si tu producto corre parte de su lógica como funciones serverless, esta reescritura te cambia tres ecuaciones a la vez: compatibilidad real con Node, bundles más grandes sin penalty y cold start más bajo por caché compartido entre isolates.

Acciones concretas que podés implementar esta semana:

  • Auditar qué dependencias de tu app ya están tirando de import.meta.resolve() o del namespace real de require('node:module').createRequire() y dejá de polyfillarlas a mano: con el flag activo se comportan como en Node puro.
  • Si usás Vite 8 + Rolldown vía el plugin de Cloudflare, activá new_module_registry en un Worker de staging y medí tu cold start: el módulo ya no se compila upfront ni en cada isolate, así que en funciones que importan dependencias grandes el primer request debería mejorar.
  • Replanteá el techo de bundle de tu proyecto. Si venías topando contra el límite anterior, ahora podés desplegar apps Node completas (64 MiB en cualquier plan) sin tener que pelearte con tree-shaking extremo o micro-frontends.

Fuentes

¿te gustó o sirvió lo que leíste?, Por favor, comparte.

👥 ¿Quieres ir más allá de la noticia?

En nuestra comunidad discutimos las tendencias, compartimos oportunidades y nos ayudamos entre emprendedores. Sin humo, solo acción.

👥 Unirme a la comunidad

Daily Shot: Tu ventaja táctica

Lo que pasó en las últimas 24 horas, resumido para que tú no tengas que filtrarlo.

Suscríbete para recibir cada mañana la curaduría definitiva del ecosistema startup e inversionista. Sin ruido ni rodeos, solo la información estratégica que necesitas para avanzar:

  • Venture Capital & Inversiones: Rondas, fondos y movimientos de capital.
  • IA & Tecnología: Tendencias, Web3 y herramientas de automatización.
  • Modelos de Negocio: Actualidad en SaaS, Fintech y Cripto.
  • Propósito: Erradicar el estancamiento informativo dándote claridad desde tu primer café.

📡 El Daily Shot Startupero

Noticias del ecosistema startup en 2 minutos. Gratis, todos los días.

Share to...