Elffuss CodeProyecto del día
Proyecto del día · 5 de septiembre de 2026

Un mini-lenguaje de reglas en una tarde: el parser fue lo fácil, la precedencia no

Escribir un evaluador de condiciones de descuento para un backoffice, con la IA al lado. El bug estaba en la tabla de precedencias, y el prompt llevaba dentro la estrategia de precios del trimestre.

El IDE con IA local en el navegadorlocal · en el navegador

El encargo era pequeño y sonaba aburrido: dentro de un backoffice de tarifas, la gente de negocio quería escribir sus propias condiciones de descuento sin pedir un despliegue cada vez. Algo tipo total > 500 && pais == ‘PT’ || cupon in [‘BF24’, ‘BF25’]. Nada de eval y nada de aceptar JavaScript de usuario: un mini-lenguaje propio, con su tokenizador, su parser y su evaluador.

Empecé por lo tonto, que es por donde hay que empezar: el tokenizador. Números, cadenas, identificadores con punto (cliente.pais), operadores de dos caracteres, posiciones para los mensajes de error. Eso un modelo lo escribe entero y bien, porque es trabajo repetitivo con reglas claras. Lo pedí, lo leí, cambié tres cosas y seguí.

El parser fue lo fácil; la precedencia, no

La primera versión fue un descenso recursivo con una función por nivel: parseOr, parseAnd, parseComparison. Funciona, pero cada operador nuevo son dos funciones más y un rediseño. Le pedí reescribirlo como parser de Pratt, con una tabla de precedencias, y ahí la conversación se puso interesante: la tabla que salió colocaba el not unario por debajo del &&.

Traducido: !activo && premium se parseaba como !(activo && premium).

Un descuento que se aplica al revés no revienta. Se cobra.

Ningún test feliz lo pilla. Lo pillé porque en vez de pedir más código le pedí otra cosa: que me imprimiera el AST de una lista de expresiones y lo comparara con lo que yo esperaba. Ahí es donde una IA que tienes al lado, sin contar peticiones, cambia cómo trabajas:

El resto de la tarde fue lo previsible: cortocircuito de verdad (que && no evalúe la derecha), decidir qué pasa cuando un campo viene null — decisión de negocio, no del parser — y errores con la columna exacta para que el de tarifas vea dónde le falta el paréntesis.

Por qué nada de esto salió de la máquina

Aquí no había datos personales de nadie. Había algo que se protege menos y duele parecido: la lógica comercial. Los ejemplos que le pasaba a la IA no eran genéricos. Eran los umbrales reales por país, nombres de campañas sin lanzar y la forma exacta en que la empresa segmenta a sus clientes. Un prompt con veinte de esas expresiones es la política de precios del trimestre en texto plano.

Con el modelo corriendo dentro del navegador, sobre la GPU del propio equipo, esa pregunta —¿esto se puede pegar o no?— simplemente no aparece. No hay petición que salga, no hay cuenta, no hay registro en el historial de nadie. Y como efecto lateral tonto pero real: funciona en un tren sin cobertura, que es donde acabé cerrando la tabla de precedencias.

El lenguaje tiene ocho operadores y cabe en un fichero. Ni es impresionante ni falta que hace. Es exactamente el tipo de utilidad pequeña y fiddly donde tener la IA al lado ahorra la tarde entera, siempre que la conversación se quede entre tú y tu editor.

Abre Elffuss Code y escribe el tuyo: el modelo corre entero en tu navegador, sobre tu GPU, y ni el código ni el prompt suben a ningún sitio.

Abrir Code →
nada de esto se sube a ningún sitio