Tu programa funciona porque eres su único usuario

Construiste con IA algo que resuelve un problema real y funciona. Antes de cobrarle a un desconocido: lo que tu programa da por cierto y deja de serlo el día que tiene un segundo usuario.

Por Jorge Castro Con asistencia de ARK 10 min de lectura
Tu programa funciona porque eres su único usuario

La primera vez que desconfié del código que escribía una máquina fue con Dreamweaver, y de eso hace tantos años que prefiero no contar cuántos. Después me certifiqué en .NET y fue el mismo caso, si bien el IDE armaba interfaces enteras con drag & drop, lo que quedaba detrás era una carnicería con poca higiene, y cuando apareció Laravel y todo el mundo hablaba de lo rápido que se construía con él, me negué a usarlo durante años por exactamente la misma razón, porque no estaba dispuesto a entregarle a un paquete la estructura de control, la autogeneración de archivos y el manejo de sesión, todo junto y sin mirar. Debo reconocer que lo odiaba. No puedo vivir sin controlar mis desarrollos, jaja.

Terminé usándolo igual y terminé enamorado, claro. Cuando por fin lo probé en un proyecto real y vi cuánto se ahorraba con el scaffold, me hice una pregunta que hoy me da algo de gracia: si esto autogenera código, ¿por qué no autogenera módulos completos? Si al final la mayoría de los CRUD son lo mismo, listar, agregar, modificar y borrar. Me pasé meses probando generadores, terminé aportando código a uno de ellos y entré a su organización, y en todo ese tiempo nunca se me ocurrió la pregunta que de verdad importaba, la que se responde sola siete años después: qué pasa cuando lo generado no es un módulo, sino el programa entero.

Eso es lo que estás haciendo tú ahora. Hablando con un modelo, en tardes sueltas, sin pedirle permiso a nadie, construiste el programa que siempre quisiste, y resuelve un problema que tenías de verdad, y lo abres todos los días, y funciona.

Entonces alguien te dice lo que era inevitable: esto lo podrías vender.

Tiene razón en algo importante, construiste algo que a ti te sirve y eso es más de lo que consigue casi toda la gente que solo habla de sus ideas. Lo que viene no tiene que ver con si eres capaz. Tiene que ver con una diferencia bastante concreta entre lo que tienes y lo que estás a punto de prometer.

Tu programa funciona porque tiene exactamente un usuario, y ese usuario eres tú.

Nunca escribiste en ninguna parte que quien lo usa es quien lo programó, que confía en él, que no tiene ningún motivo para atacarlo, que los datos guardados le pertenecen, que si se cae puede levantarlo, y que sabe perfectamente qué debería estar haciendo. No hacía falta escribirlo. Lo cumplías tú, todos los días, sin darte cuenta de que lo estabas cumpliendo. Venderlo es dejar de cumplirlo todo a la vez.

Ahora te muestro las cuatro cosas que te vas a decir a ti mismo, y por qué ninguna de las cuatro te va a salvar.

”Las consultas están bien, las probé todas.”

En tu programa, esta consulta está perfecta:

SELECT * FROM notas WHERE id = ?

Y está perfecta de verdad, no es que te la esté pasando por alto, todas las notas son tuyas, no hay frontera entre dueños porque hay un solo dueño y tú eres ese dueño. El día que existen dos cuentas, esa misma consulta es una filtración, y cualquiera puede mandar cualquier número y recibir la nota de otra persona. La versión que no filtra lleva una condición más:

SELECT * FROM notas WHERE id = ? AND usuario_id = ?

Parece un detalle menor y es básicamente todo lo que quiero decirte con este artículo, porque no basta con acertar una vez, hay que acertar en todas las consultas, en las que escribas el mes que viene, y en las que escriba el modelo cuando le pidas una función nueva y ya ni revises el SQL porque las diez anteriores salieron bien. Una sola consulta a la que le falte esa condición no te expone los datos de un cliente, te expone los de TODOS, los de la persona que te pagó ayer y los de la que te iba a pagar mañana.

Antes de seguir leyendo, abre el proyecto y cuenta cuántas de tus consultas filtran por el dueño del dato. Si la respuesta no es “todas”, ya sabes en qué vas a trabajar esta semana.

”El modelo de datos lo fui armando sobre la marcha, pero está ordenado.”

No está ordenado, y no es culpa tuya, es que no se diseñó, se fue sedimentando.

Son cuarenta conversaciones en las que pediste un cambio, el modelo lo hizo, funcionó y seguiste adelante, y quedaron columnas que ya nadie escribe, tablas que significan una cosa en las filas viejas y otra en las nuevas, y decisiones de marzo que contradicen a las de junio. Mientras el dato es tuyo, eso es deuda tuya, la pagas cuando quieras, o no la pagas nunca y no pasa absolutamente nada.

Cuando el dato es de alguien que te paga, cambia de naturaleza. Una migración mal hecha ya no te arruina la tarde, le pierde información a una persona que confió en ti, y responder “lo restauro del respaldo” da por hecho tres cosas seguidas: que tienes respaldos, que alguna vez probaste restaurar uno, y que sabes cuánto se pierde entre el último respaldo y el accidente. Un respaldo que nunca restauraste es un archivo con muy buenas intenciones.

Intenta escribir en una hoja qué significa cada tabla, sin abrir el código. Las que no puedas explicar en una línea son exactamente las que te van a doler.

”Si algo falla lo reinicio y listo.”

En tu máquina, cuando algo falla te enteras porque lo estás usando, cierras y vuelves a abrir, y para un solo usuario esa es una estrategia de operación perfectamente razonable.

Con clientes esa misma pregunta cambia de forma, y si bien sigue pareciendo la misma, ya no es qué haces cuando se cae, es cómo te enteras de que se cayó. Si la respuesta es “porque lo abro y no carga”, tus clientes lo van a saber antes que tú, y tu primer aviso de que algo anda mal va a llegar dentro de un correo escrito por alguien que está molesto y que además te está pagando. Ese correo es hoy tu sistema de monitoreo.

Apágalo a propósito un día cualquiera y mide cuánto tardas en notarlo sin mirarlo. Ese número es tu tiempo de reacción real, y nunca lo mediste porque hasta ahora no hacía falta.

”Elegí SQLite porque es más simple.”

Este es el punto donde yo me equivoqué durante años en la dirección contraria, y también el que peor se cuenta por ahí.

La versión que circula dice que el modelo eligió SQLite y que para un SaaS necesitas Postgres, y si bien la primera mitad suele ser verdad, la segunda no siempre lo es, porque SQLite corre cargas de producción reales y hay productos serios construidos encima. Si tu programa tiene un servidor, escrituras poco frecuentes y no vas a repartirlo en varias máquinas, SQLite te sirve y te va a ahorrar trabajo. Si esperas escrituras concurrentes desde varios procesos, ahí sí vas a querer Postgres, y mejor antes que después.

Y acá viene lo que a mí me importa, que no tiene que ver con SQLite: nadie se sentó nunca a elegirlo, y si bien una elección y un default se parecen muchísimo, se parecen solo hasta el día exacto en que dejan de parecerse. Un default que aceptaste sin evaluar sigue siendo un default aunque la respuesta resulte correcta de casualidad, porque no lo puedes defender, no sabes bajo qué condiciones deja de servir, y no vas a ver venir el día en que deje de hacerlo.

Y acá está lo que más me costó entender a mí, que vengo de desconfiar de estas herramientas desde Dreamweaver: el modelo no toma malas decisiones, hace que los defaults se vean como decisiones, te entrega algo que funciona, y lo que funciona ya no lo cuestiona nadie, ni tú ni yo ni el que venga después.

Haz la lista de las decisiones técnicas de tu proyecto y escribe al lado de cada una por qué. Base de datos, autenticación, dónde corre, cómo se despliega. Las que no puedas completar no son decisiones tuyas, son defaults del modelo, y ahora te pertenecen igual.

Antes de que me lo discutan

Si el programa se va a borrar, nada de lo anterior aplica. Un prototipo que cumple su función y muere es un buen uso de la herramienta, y prepararlo para producción sería desperdicio. El problema aparece cuando el prototipo no se borra, que es de lo que trata este texto.

También existe una posición legítima que sostiene que buena parte de este aparato sobra. Dan North lleva años argumentando, contra los principios SOLID, que la respuesta suele ser escribir código simple en lugar de añadir estructura, y si tiene razón, parte de lo que aquí echo de menos también sobra. No lo tengo resuelto y no voy a fingir que sí.

Y no, tampoco estoy diciendo que necesites contratar a alguien. Sería muy conveniente para mí, y no es lo que observo.

Lo que hay medido, y lo que no prueba

Todo lo anterior es una posición mía, no el informe de un incidente que yo haya vivido. Lo que sí está medido es esto, con sus límites puestos al lado.

DORA, el programa de investigación de Google sobre entrega de software, encontró algo que encaja incómodamente bien con todo lo que vengo diciendo: a mayor adopción de IA, mejor rendimiento de entrega y peor estabilidad, las dos cosas al mismo tiempo. Su explicación es que la aceleración no crea los problemas, los destapa, expone las debilidades que ya estaban más abajo en la cadena. Conviene agregar que la propia fuente lo presenta como correlación y no como causa.

La encuesta de Stack Overflow del mismo año llega al mismo sitio por otro camino. La frustración más citada, por dos tercios de quienes respondieron, son las soluciones de IA “casi correctas, pero no del todo”. Es percepción declarada y no medición de defectos, y quien contesta esa encuesta suele ser gente ya muy involucrada con esa comunidad.

GitClear, que analiza repositorios, reporta que la duplicación de bloques de código casi se duplicó desde 2023 mientras la refactorización se desplomaba, con dos advertencias que su propio informe no hace: es un proveedor de analítica midiendo repositorios de sus clientes, y no distingue correlación de causalidad.

Ninguna de las tres demuestra que tu programa vaya a fallar. Lo que muestran juntas es que el problema no está en la calidad del código generado, está en que la velocidad de producción subió y todo lo que viene después siguió costando exactamente lo mismo que antes.

Yo fallé en la mitad contraria

Volviendo a donde empecé, con mi desconfianza de Dreamweaver y mis años negándome a usar Laravel: escribí hace un mes que llevaba quince años construyendo software y cero ventas, y el diagnóstico honesto fue que nunca construí la otra mitad.

Tenía todo lo que este artículo describe. Sabía diseñar el modelo de datos, sabía desplegarlo, sabía exactamente dónde estaban los agujeros, y no me sirvió de nada, porque nunca aprendí a poner eso delante de alguien dispuesto a pagarlo.

Tú tienes la mitad que a mí me faltaba. Construiste algo que resuelve un problema y tuviste el impulso de enseñarlo. Ninguna de las dos mitades sola es un producto, yo aprendí la mía tarde y por el lado caro, y este texto existe para que la otra te salga más barata de lo que me salió a mí la mía.

Por dónde empezar

Sé que me alargué, pero de verdad hay mucho que decir acá, así que te lo dejo en orden y corto.

No empieces por reescribirlo. Empieza por el filtro de las consultas, que es lo único de todo esto capaz de hacerte daño de verdad esta semana. Después, la lista de decisiones con su porqué al lado. Ese documento de una página es toda la diferencia entre un programa que funciona y un programa que entiendes, y es lo único de este artículo que no te puede escribir un modelo, porque la mitad de las respuestas no están en el código.

P.D.: si vas a cobrar por esto, revisa además dos cosas que no alcancé a meter arriba, dónde están guardadas las claves de tus servicios y qué pasa con los datos de una persona que te pida borrar su cuenta. Las dos se arreglan en una tarde ahora y en ninguna tarde después.

Artículos relacionados

Volver al blog ↗