← Volver a contenidos

Bun nunca prometió reemplazar a Node.js al 100% — ¿Eso es bueno o malo?

nodejs bun runtime research

Bun nunca prometió reemplazar a Node.js al 100% — ¿Eso es bueno o malo?

TL;DR: Bun apunta a 90% de compatibilidad con Node.js, no 100%. Funciona bien para APIs simples con Express/Hono, CLIs, y proyectos nuevos. Puntos de fricción: Next.js funciona como package manager pero el runtime tiene edge cases en producción; Prisma requiere Node.js instalado para el CLI; Playwright/Puppeteer problemáticos en Windows; crypto 10-14x más lento. Audita tu stack antes de migrar—las regresiones entre versiones son reales.


Si has estado siguiendo el ecosistema JavaScript en los últimos años, probablemente has escuchado que Bun es “el reemplazo de Node.js”. Más rápido, más moderno, todo-en-uno. La promesa suena irresistible: cambia node por bun y tu aplicación vuela.

Pero hay un problema. Esa promesa nunca existió exactamente así.

En este artículo vamos a investigar qué prometió realmente Bun, cuál es el estado actual de compatibilidad, y—lo más importante—si puedes confiar en él para tu stack específico. Spoiler: la respuesta depende mucho de lo que estés construyendo.


La promesa que nunca existió

Desde su lanzamiento en 2022, Bun se posicionó como un “drop-in replacement” para Node.js. Jarred Sumner, su creador, lo describió así en una entrevista con JavaScript Jabber:

“Está diseñado como un reemplazo directo de Node.js. Aún no estamos al 100%. Estamos reimplementando básicamente todas las APIs de Node.js desde cero. Es una montaña de trabajo. Pero hemos hecho mucho progreso.”

La palabra clave aquí es “aún”. Bun nunca prometió compatibilidad total desde el día uno—prometió trabajar hacia ella. Pero aquí está el detalle que muchos pasan por alto: según el roadmap oficial de Bun, el objetivo es 90% de compatibilidad, no 100%.

¿Por qué 90%? Porque algunas APIs de Node.js simplemente no tienen sentido en la arquitectura de Bun. node:v8 es el ejemplo obvio—Bun usa JavaScriptCore (el motor de Safari), no V8.

El cambio silencioso de enfoque

Si observas la evolución de Bun, notarás algo interesante. Mientras la comunidad esperaba que cada release cerrara más gaps de compatibilidad con Node.js, Bun empezó a construir cosas completamente nuevas:

  • Bun.sql: Cliente nativo de PostgreSQL, MySQL y SQLite (introducido en v1.2, expandido en v1.3)
  • Bun.s3: Cliente nativo de S3 (5x más rápido que @aws-sdk/client-s3)
  • Bun.redis: Cliente nativo de Redis/Valkey (introducido en v1.2.9, destacado en v1.3)
  • HTML Imports: Una feature que Node.js no tiene (experimental en v1.1.44, oficial en v1.2)
  • Hot reloading integrado: Sin necesidad de nodemon (mejorado en v1.3)

Esto no es necesariamente malo. Pero sí revela una verdad incómoda: Bun no está tratando de ser “Node.js pero rápido”—está construyendo algo diferente.

El factor Anthropic

En diciembre de 2025, Anthropic adquirió Bun. Jarred Sumner explicó que Bun ahora potencia Claude Code, Claude Agent SDK, y otros productos de IA.

Las promesas post-adquisición:

  • Bun sigue siendo open-source y MIT
  • El mismo equipo continúa el desarrollo
  • El roadmap mantiene el foco en compatibilidad con Node.js

Pero ahora hay un stakeholder con intereses específicos. Anthropic necesita velocidad, estabilidad, y sí—compatibilidad con Node.js. Eso podría ser bueno para todos. O podría significar que las prioridades se alineen más con las necesidades de productos de IA que con el ecosistema general.


El estado real de compatibilidad

Dejemos los titulares y veamos los números. Bun ejecuta el test suite de Node.js antes de cada release. Según la documentación oficial de compatibilidad, estos son los resultados por módulo:

Módulos con alta compatibilidad (>95%)

MóduloTest Suite Pass Rate
node:events100%
node:os100%
node:path100%
node:zlib98%
node:http295.25% (test suite de gRPC)
node:dns>90%
node:dgram>90%

Nota: gRPC (Google Remote Procedure Call) es un framework de comunicación entre servicios que depende fuertemente de HTTP/2. Bun usa el test suite de gRPC como benchmark para validar su implementación de node:http2 porque representa casos de uso reales y exigentes del protocolo.

Módulos con compatibilidad media (80-95%)

MóduloTest Suite Pass RateNotas
node:fs92%Falta fs.openAsBlob en algunas versiones
node:streams82%Comportamiento edge-case diferente
node:http~85%Request body se bufferea en lugar de streamear

Nota: fs.openAsBlob permite leer archivos directamente como objetos Blob, útil para subir archivos a APIs web o procesarlos con Web Streams sin cargarlos completamente en memoria.

Lo que falta completamente

Estos módulos no están implementados, y aunque no los uses directamente, probablemente alguna dependencia en tu proyecto sí:

  • node:inspector: No implementado. Bun tiene su propio debugger con WebKit Inspector Protocol (--inspect), pero la API de Node.js no está disponible.

    • Paquetes afectados: Sentry (monitoreo de errores), elastic-apm-node (Elastic APM), y otras herramientas de monitoreo que dependen de este módulo para profiling.
  • node:repl: No implementado. Bun tiene su propio REPL básico (bun repl), pero no expone la API programática de Node.js.

    • Paquetes afectados: Vorpal (framework para CLIs interactivas), y herramientas que crean interfaces REPL personalizadas.
  • node:sqlite: Irónico dado que Bun tiene SQLite nativo (bun:sqlite), pero la API de Node.js no está implementada.

    • Paquetes afectados: better-sqlite3 tiene problemas de ABI incompatible—el módulo fue compilado contra una versión de Node.js diferente. Workaround: instalar con npm install en lugar de bun install, o migrar a bun:sqlite directamente.
  • node:trace_events: No implementado. Solo existe un stub vacío—funciones que existen para que el código no falle al importar el módulo, pero no hacen nada. Esto evita errores de “module not found” pero el tracing simplemente no funciona.

Limitaciones críticas en módulos parciales

node:cluster (documentación)

node:child_process (Issue #6743)

  • No puede enviar socket handles via IPC—el argumento sendHandle es undefined
  • Esto rompe patrones comunes de arquitectura multi-proceso donde el padre distribuye conexiones a workers

node:http2 (documentación)

  • Cliente y servidor implementados (95.25% del test suite de gRPC pasa)
  • Falta http2stream.pushStream (HTTP/2 Server Push)
  • Falta soporte para la extensión ALTSVC
  • Falta options.allowHTTP1 y options.enableConnectProtocol

node:crypto — El elefante en la sala

Las funciones de crypto en Bun son significativamente más lentas que en Node.js. Múltiples issues documentan el problema:

Si tu aplicación hace hashing intensivo, encriptación, o cualquier trabajo criptográfico pesado—no uses Bun.


La prueba de fuego: ¿Funciona tu stack?

Los números de test suites están bien, pero lo que realmente importa es: ¿funcionan los paquetes que uso todos los días?

Investigué 14 paquetes populares en diferentes industrias. Aquí está el veredicto:

Frameworks Web

Express

MétricaResultado
¿Funciona?✅ Sí
Performance3x más rápido que en Node.js
Memoria~2x más uso de RAM

Fastify

MétricaResultado
¿Funciona?✅ Sí, pero…
PerformanceMás lento que en Node.js en algunos benchmarks
RecomendaciónUsa Bun.serve() directamente (3-4x más rápido)

Jarred Sumner lo dijo directamente:

“Fastify no es rápido en Bun. Bun.serve() es 3x-4x más rápido.”

NestJS — Oficialmente soportado, pero con matices

Jarred Sumner abrió el issue #1641 para trackear la compatibilidad con NestJS. Ese issue está cerrado como COMPLETED, lo que significa que Bun considera que tiene la compatibilidad necesaria para ejecutar NestJS.

Feature¿Funciona?Detalle
Decorators✅ SíDesde Bun 1.0.3
Core features✅ SíIssue oficial cerrado como completado
TypeORM integration⚠️ Variablerequire('module').globalPaths causaba problemas (arreglado en canary builds)
Producción bajo carga⚠️ Reportes mixtosCrashes reportados en algunos casos

Contexto importante: El equipo de NestJS no ha declarado soporte oficial para Bun. Esto significa que si encuentras bugs, puede que ninguno de los dos equipos los priorice. Sin embargo, la comunidad ha reportado éxito en proyectos de producción.

Hono

Feature¿Funciona?Detalle
Todo✅ SíDiseñado para Bun

Next.js — El caso más complejo

La situación de Next.js ha cambiado significativamente. En enero 2025, Bun removió la advertencia de incompatibilidad que decía “Next.js App Router is incompatible with Bun”.

Uso¿Funciona?Detalle
Package manager✅ Síbun install, bun run build funcionan perfectamente
Runtime (desarrollo)⚠️ VariableHot reload inconsistente reportado
Runtime (producción)⚠️ Con issuesMeta tags en <body> al refrescar (Next 15.4+)
APIs nativas de Bun⚠️ Limitadoimport { S3Client } from "bun" no funciona con Turbopack (fix mergeado en PR #77616)
Streaming responses⚠️ Problemas”ReadableStream is locked” en Next 16 + Bun 1.3.2

La realidad: Bun como package manager para Next.js funciona excelente. Bun como runtime todavía tiene edge cases problemáticos. La documentación oficial de Bun ahora incluye guías para App Router, pero en producción muchos desarrolladores reportan que Node.js sigue siendo más estable.

Recomendación: Usa bun install y bun run build, pero considera node para el servidor de producción si encuentras issues.


Real-time y Colas

Socket.IO

Setup¿Funciona?Detalle
Directo⚠️ LimitadoRequiere configuración especial
Con @socket.io/bun-engine✅ SíEngine nativo de Bun desarrollado por el equipo de Socket.IO

Nota: A menos que necesites fallback a polling, considera usar WebSockets nativos de Bun directamente—son significativamente más rápidos.

BullMQ

MétricaResultado
¿Funciona?⚠️ Parcial
Performance boostSolo ~20% (bottleneck en IORedis)
Bun.redisNo soportado aún

Auth y Pagos

bcrypt (nativo)

Feature¿Funciona?Detalle
Original❌ NoAddon nativo incompatible, segfaults reportados
Alternativas✅ SíUsa Bun.password (nativo) o bcryptjs

Bun tiene hashing de passwords integrado:

const hash = await Bun.password.hash("mi-password");
const valid = await Bun.password.verify("mi-password", hash);

Stripe

Versión Bun¿Funciona?Detalle
1.1.4✅ SíFunciona correctamente
1.1.5❌ NoRegresión que rompió Stripe
1.1.6+⚠️ VariableVerifica con tu versión

Las regresiones son un problema real. Un upgrade de Bun puede romper integraciones críticas.


Cloud y AWS

AWS SDK v3

Feature¿Funciona?Detalle
Servicios básicos✅ SíS3, DynamoDB, etc. funcionan
S3 con SDK✅ Sí5x más rápido que en Node.js desde Bun 1.1.25
Bun.s3 nativo✅ Recomendado5x más rápido que @aws-sdk/client-s3

Si solo necesitas S3, considera usar Bun.s3 directamente en lugar del SDK.


ORMs y Bases de Datos

Prisma

Operación¿Funciona?Detalle
Queries✅ SíEl cliente funciona
prisma generate⚠️ Requiere Node.jsEl CLI se cuelga si Node no está instalado
prisma migrate⚠️ Requiere Node.jsMismo problema
Docker⚠️ ProblemáticoErrores de Query Engine por arquitecturas incompatibles

El equipo de Prisma está trabajando en un nuevo generador “Rust-free” que mejora la situación, pero hoy necesitas Node.js instalado aunque ejecutes tu app con Bun.

TypeORM

Feature¿Funciona?Detalle
Decorators básicos✅ SíDesde Bun 1.0.3 con emitDecoratorMetadata
Casos edge⚠️ ProblemáticoReportes de Cannot find module con metadata internos

Drizzle ORM

Feature¿Funciona?Detalle
Todo✅ SíSoporte nativo, integración con Bun.sql

Veredicto: Usa Drizzle si empiezas un proyecto nuevo. Si ya tienes Prisma, mantén Node.js en tu toolchain.

Mongoose

Feature¿Funciona?Detalle
Conexión básica✅ SíMongoDB driver funciona
Todas las features✅ SíDocumentación oficial de Bun confirma compatibilidad

Browser Automation

Puppeteer

Plataforma¿Funciona?Detalle
Linux✅ SíFunciona desde Bun 1.1
macOS✅ SíFunciona desde Bun 1.1
Windows⚠️ InestableComportamiento impredecible, exits aleatorios

Playwright

Plataforma¿Funciona?Detalle
Linux✅ SíFunciona desde Bun 1.1
macOS✅ SíFunciona desde Bun 1.1
Windows⚠️ ParcialNamed pipes implementados en v1.1.29+, pero aún hay reportes de timeouts

Veredicto: Si desarrollas en Windows o tu CI corre en Windows, quédate con Node.js.


Procesamiento de Imágenes

Sharp

Operación¿Funciona?Detalle
Runtime✅ SíFunciona una vez instalado
bun install❌ NoPostinstall scripts no compatibles
Segfaults⚠️ ReportadosEn Docker y operaciones concurrentes

Workaround: Instala con npm install sharp y luego usa bun para ejecutar.

node-canvas

Feature¿Funciona?Detalle
Original❌ NoUsa node-gyp que requiere compilación nativa
@napi-rs/canvas⚠️ Con issuesProblemas con musl/glibc, crashes en executables

Nota: @napi-rs/canvas no requiere node-gyp, pero tiene sus propios issues con Bun. Verifica la compatibilidad con tu versión.


Bots y Gaming

Discord.js

Feature¿Funciona?Detalle
Texto/comandos✅ SíFunciona correctamente
Voice channels❌ No@discordjs/voice falla porque @discordjs/opus (nativo) no carga correctamente y hay problemas de conexión

Veredicto: Si solo necesitas un bot de texto, adelante. Si necesitas audio, quédate con Node.js.


El elefante en la sala

Mirando la lista anterior, surge una pregunta obvia: ¿Por qué Bun construye clientes nativos de S3, Postgres y Redis antes de completar la compatibilidad con Node.js?

La respuesta oficial del equipo de Bun en su documentación de Bun.sql:

“Creemos que es más simple para los desarrolladores tener un driver de base de datos integrado en Bun. El tiempo que pasas eligiendo librerías es tiempo que podrías estar construyendo tu app.”

Y hay una razón técnica:

“Aprovechamos algunos internals del motor JavaScriptCore para hacer más rápida la creación de objetos de formas que serían difíciles de implementar en una librería.”

En otras palabras: estas features nativas son significativamente más rápidas que sus equivalentes en npm precisamente porque están integradas en el runtime.

Pero esto crea una tensión. Cada hora de ingeniería dedicada a Bun.redis es una hora no dedicada a arreglar node:cluster en macOS. Es una decisión de producto legítima, pero debes entender las implicaciones:

Bun está apostando a que prefieres features nuevas y rápidas sobre compatibilidad perfecta con el ecosistema existente.

Si tu prioridad es migrar un proyecto Node.js existente sin sorpresas, esa apuesta puede no alinearse con tus necesidades.


Los fantasmas en producción

Más allá de la compatibilidad de APIs, hay problemas de estabilidad que debes conocer.

Segfaults bajo carga

En diciembre de 2024, un desarrollador reportó crashes aleatorios en producción:

“Segfaults aleatorios pasando docenas de veces al día, correlacionando aproximadamente con períodos de mayor carga.”

El problema desapareció al volver a Bun 1.1.33 desde 1.1.38. Docker reiniciaba el container automáticamente, pero el problema persistía hasta el rollback.

Regresiones que rompen paquetes

El caso de Stripe es ilustrativo. La versión 1.1.5 de Bun rompió la integración con Stripe. La solución fue hacer downgrade a 1.1.4.

Esto significa que no puedes asumir que un upgrade de Bun es seguro. Necesitas un pipeline de CI que pruebe tus integraciones críticas antes de actualizar.

El problema de Windows

Múltiples paquetes (Playwright, Puppeteer, y otros) tienen problemas específicos en Windows que no existen en Linux o macOS. Si tu equipo desarrolla en Windows o tu CI corre en Windows, vas a encontrar más fricción.


Veredicto: ¿Deberías hacer el switch?

Después de toda esta investigación, aquí está mi framework de decisión:

Usa Bun si…

  • ✅ Construyes CLIs o herramientas de desarrollo (el single-binary es genial para distribución)
  • ✅ Desarrollas APIs simples con Hono o Elysia (frameworks diseñados para Bun)
  • ✅ Tu stack es Express básico sin dependencias nativas complejas
  • ✅ Necesitas SQLite, Postgres o S3 y quieres máxima performance
  • ✅ Es un proyecto nuevo donde puedes elegir dependencias Bun-friendly
  • ✅ Desarrollas en Linux o macOS (Windows tiene más issues)

No uses Bun si…

  • ❌ Haces trabajo criptográfico intensivo (10-14x más lento que Node.js)
  • ❌ Tu CI o equipo desarrolla en Windows (Playwright, Puppeteer, y otros tienen issues)
  • ❌ Necesitas compatibilidad perfecta con un codebase Node.js existente grande
  • ❌ Usas native addons como node-canvas, bcrypt nativo, sharp (sin workarounds)
  • ❌ Dependes de Discord.js con audio

Evalúa cuidadosamente si…

  • ⚠️ Usas Next.js — funciona como package manager, pero el runtime tiene edge cases (streaming, meta tags, hot reload)
  • ⚠️ Usas NestJS — oficialmente “compatible” pero sin soporte del equipo de NestJS
  • ⚠️ Dependes de Prisma — el cliente funciona pero el CLI requiere Node.js instalado

Checklist de auditoría pre-migración

Antes de intentar migrar, responde estas preguntas:

1. ¿Usas módulos nativos?

Ejecuta este comando para identificarlos:

npm ls | grep -E "(native|binding|addon)"

Según la documentación de Bun sobre módulos, los addons N-API deberían funcionar, pero los que dependen de node-gyp pueden fallar.

N-API (Node-API) es la interfaz estable de Node.js para crear extensiones nativas en C/C++. A diferencia de las APIs internas de V8 que cambian entre versiones, N-API garantiza compatibilidad binaria—un addon compilado para Node 14 funciona en Node 20 sin recompilar. Bun reimplementa esta API para que los addons existentes funcionen sin modificaciones.

Alternativas comunes:

Paquete nativoAlternativa Bun-friendly
bcryptbcryptjs o Bun.password
node-canvas@napi-rs/canvas (con limitaciones)
better-sqlite3bun:sqlite nativo

2. ¿Tu proyecto tiene >50k líneas de código?

Un desarrollador documentó la migración de un monorepo con 300+ paquetes y ~100,000 líneas. Sus conclusiones:

“Terminé removiendo la mayoría de referencias a Bun.* y asegurando que donde uso el global bun, lo importe así: import Bun from 'bun'. De esta forma todo puede correr en Node también.”

La recomendación: mantén compatibilidad dual hasta estar seguro de que todo funciona.

3. ¿Desarrollas o deployeas en Windows?

Bun 1.1 agregó soporte oficial para Windows, pero con limitaciones:

Considera usar WSL o contenedores Linux para desarrollo si tu equipo está en Windows.

4. ¿Tus tests cubren integraciones críticas?

Antes de migrar, ejecuta tu suite de tests con Bun:

bun test

Como vimos con el caso de Stripe, las regresiones son reales. La guía de migración a producción recomienda:

“Monitorea las tasas de error obsesivamente las primeras 48 horas. Si algo se rompe, un comando revierte el deployment.”

5. ¿Puedes hacer rollback rápido?

Bun convierte automáticamente package-lock.json a bun.lock, preservando las versiones resueltas. Pero mantén tu lockfile original:

# Guarda el lockfile original
cp package-lock.json package-lock.json.backup

# Migra a Bun
bun install

# Si algo falla, rollback inmediato
mv package-lock.json.backup package-lock.json
rm bun.lock
npm install

6. ¿Tus dependencias tienen postinstall scripts?

A diferencia de npm, Bun no ejecuta lifecycle scripts por defecto por seguridad. Solo los paquetes en el top 500 de npm están en la allowlist.

Para ver qué scripts fueron bloqueados:

bun pm untrusted

Para confiar en un paquete específico:

bun pm trust <nombre-paquete>

O agrégalo a tu package.json:

{
  "trustedDependencies": ["sharp", "puppeteer", "@prisma/client"]
}

Después de agregar, reinstala:

rm -rf node_modules
rm bun.lock
bun install

Conclusión

Bun es un proyecto impresionante con una visión clara: hacer JavaScript más rápido y simple. Pero esa visión no es ser una copia de Node.js.

La pregunta “¿Puedo reemplazar Node.js con Bun?” tiene una respuesta honesta: depende de tu stack específico. Para algunos proyectos, Bun es estrictamente mejor. Para otros, es un downgrade funcional.

Lo más importante que debes recordar:

  1. El objetivo es 90% de compatibilidad, no 100%
  2. Las features nuevas (S3, Redis, Postgres) compiten por recursos con la compatibilidad
  3. Windows tiene más problemas que Linux/macOS
  4. Las regresiones entre versiones son reales—no asumas que upgrades son seguros
  5. Audita tu stack antes de migrar

Bun no prometió reemplazar Node.js al 100%. Y ahora sabes exactamente qué significa eso para tu proyecto.