Qué se siente programar en Zig viniendo de Rust: caso real

Por qué un desarrollador senior de Rust se pasó a Zig (y qué encontró)

Un programador con siete años escribiendo Rust reimplementó en Zig su librería de JSONPath (el lenguaje de consulta para JSON especificado en el estándar RFC 9535) y publicó un balance honesto de lo que significa migrar de un lenguaje con memoria gestionada por el compilador a uno donde cada byte se pide y se libera a mano. El caso sirve como radiografía del estado actual de Zig y como guía práctica para founders que evalúan stacks de bajo nivel.

La experiencia confirma lo que reportan otros practicantes: Zig está en la versión 0.14 a la fecha de la comparativa de Sinclair Target publicada en agosto de 2025, su biblioteca estándar tiene "casi cero documentación", y la mejor forma de aprenderlo sigue siendo leer el código fuente directamente. La promesa sigue siendo la misma desde hace años: convertirse en el sucesor real de C para sistemas de bajo nivel, con compilación rápida, binarios pequeños y control total sobre el hardware.

Qué ganó (y qué perdió) al reimplementar JSONPath en Zig

El proyecto se llama zig-jsonpath y es un clon 1:1 de la versión Rust ya existente (jsonpath-rust). Reimplementar el mismo proyecto en otro lenguaje es una de las formas más fiables de comparar productividades reales, porque elimina el sesgo de "es más fácil porque ya conozco el problema". Cuatro hallazgos destacan:

👥 ¿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

1. IDE y tooling: volver a la consola. En Rust el autor usaba RustRover y otros JetBrains; en Zig no hay nada equivalente. "Terminé migrando de un IDE completo a un setup con helix + alacritty + zellij", cuenta. El sistema de build (build.zig) reemplaza toda la parafernalia con tres comandos:

  • zig build test corre toda la suite
  • zig build test -Dfilter="..." filtra por nombre
  • zig build check une unit tests + compliance

2. Estructura plana por defecto. Mientras que el árbol Rust del proyecto tiene carpetas anidadas (parser/grammar/, query/filter/, etc.), la versión Zig vive en cinco archivos en la raíz: root.zig, parser.zig, model.zig, model_query.zig, query.zig. La filosofía de Zig, heredada de C, penaliza ligeramente cada nivel extra de anidamiento, así que la presión cultural empuja a mantener todo en un mismo archivo hasta que el proyecto realmente lo justifique.

3. Sin paradigma funcional. Rust permite escribir la librería con combinadores monádicos, flat_map, reduce, tipos suma y closures. En Zig eso se traduce en mutación in-place, bucles while, defer/errdefer y fork() para copiar estados. El código Zig resultante es, según el autor, menos legible que su equivalente Rust, pero más cercano al modelo mental de C.

4. Allocators: la gran diferencia cultural. Como apunta Sinclair Target, "en Zig, asignas cada byte tú mismo, explícitamente" y "tienes más control incluso que en C: para asignar bytes tienes que llamar a alloc() sobre un tipo específico de allocator". En la práctica eso significa que casi toda función recibe un allocator como parámetro y toda estructura lo almacena, lo cual vuelve al programador responsable del ciclo init/deinit en cada rama del flujo de control.

El día a día con memoria manual: cuatro bugs que Rust no puede tener

Lo más valioso del artículo no es la comparativa filosófica, sino los ejemplos concretos de bugs que el autor cazó con TestAllocator y FailingAllocator durante el desarrollo. Son los mismos patrones que cualquier equipo migrando a Zig encontrará en producción.

Caso 1 — Leak por olvidar deinit.

var iter = q.JsonPathIter.init(&root, std.testing.allocator);
try iter.append(&root, "$['a']");
// BUG: no hay iter.deinit()

La detección apunta a la llamada dupe dentro de append. En Rust esto no compila: Drop corre al salir del scope automáticamente.

Caso 2 — Leak por error path. Si la segunda llamada a append falla, iter se filtra porque nadie llamó deinit en la rama de error. La solución es errdefer iter.deinit(); justo después del init. En Rust el operador ? ejecuta Drop incondicionalmente, así que la categoría de bug desaparece por construcción.

Caso 3 — Double free entre capas. Cuando un resultado se mueve a un cache y la capa intermedia también intenta liberarlo, el TestAllocator detecta el segundo free durante el cleanup. La regla que el autor aprendió: solo una capa puede poseer el valor; las demás deben entregar la propiedad explícitamente. En Rust el move semantics hace que el código no compile si intentas usar la variable después de moverla.

Caso 4 — Asignación huérfana. Si dupe tiene éxito pero el append posterior falla, el string duplicado queda sin liberar porque iter.deinit() no sabe que existe. El patrón a aplicar es errdefer self.allocator.free(duped); entre la asignación y el uso. Rust simplemente no expone esta ventana: no hay un push "fallible" que te devuelva un valor ya alocado sin enlazar.

Lección operativa: Zig exige escribir tests específicos que ejerciten las rutas de fallo. Confiar en que el código "parece correcto" es el camino más rápido al incidente en producción.

El ecosistema, todavía joven

El autor es directo: "El ecosistema es todavía muy joven. Hay escasez real de librerías, e incluso algo tan básico como regex no está del todo maduro". La librería mvzr, el motor de regex disponible en Zig, no soporta escapes de propiedades Unicode (\p{...}), lo cual fue un hueco directo al implementar las funciones de filtro del RFC 9535. Encima, la API de la biblioteca estándar cambia entre versiones.

Este diagnóstico coincide con la evaluación externa de Sinclair Target (agosto 2025): Zig 0.14, documentación casi inexistente, idioma definitivo por construir. Para una startup eso significa que el lenguaje todavía no es apto para reemplazar C en producción crítica donde se depende de librerías maduras de terceros.

¿Qué significa esto para tu startup?

Cuándo Zig tiene sentido. Proyectos nuevos donde controlás todo el stack, con equipo chico acostumbrado a bajo nivel y donde la prioridad es latencia mínima o footprint binario (sistemas embebidos, motores de juego, infraestructura de alto rendimiento, tooling interno que necesita arranques de milisegundos).

Cuándo NO tiene sentido. Productos donde la velocidad de iteración pesa más que el rendimiento bruto, equipos sin experiencia en C o Rust, o cualquier producto que dependa de un ecosistema amplio de librerías (sobre todo machine learning, web frameworks, bases de datos cliente, etc.).

Dos acciones concretas si estás evaluando el stack:

  • Antes de elegir Zig para producción: reimplementá una pieza crítica pequeña (un parser, un codec, un worker) y medí cuánto tardás en alcanzar paridad con la versión Rust o Go. El caso del artículo (un JSONPath completo) muestra que el costo en tiempo de desarrollo es real y concentrado en la disciplina de memoria, no en el lenguaje en sí.
  • Si tu equipo ya viene de Rust: considerá quedarte en Rust para el producto y usar Zig solo en los puntos calientes de rendimiento (FFI directo entre ambos lenguajes es viable). Sacrificar la seguridad de memoria del compilador Rust en toda la base de código por ganar un poco de velocidad de compilación rara vez vale la pena.

Implicaciones para founders hispanohablantes

En LATAM y España la oferta de ingenieros con experiencia profunda en Zig es mínima y no va a crecer rápido. Invertir en Zig hoy es una apuesta de largo plazo con un riesgo real de que la versión 1.0 tarde más de lo prometido y de que el ecosistema no alcance la masa crítica necesaria. Para founders, esto se traduce en tres reglas pragmáticas: usar Rust como default para nuevos servicios de bajo nivel, mantener C solo donde hay base instalada que lo justifique, y reservar Zig para experimentación interna con un equipo senior que pueda bancar la curva de aprendizaje y el costo de mantener una librería propia cuando la del ecosistema no existe.

Fuentes

👥 ¿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...