arquitectura de software

comunicación

sistemas distribuidos

Por qué construir software es difícil: el coste de la ambigüedad

El software falla en las brechas entre objetivos, comunicación, estados del sistema y comportamiento real.

Construir software es difícil porque el código es solo la parte visible del sistema. El trabajo más complejo es acordar qué debe significar el sistema cuando intervienen personas, dispositivos, tiempo real y fallos reales.

Para un fundador, esto aparece como retrasos, retrabajo y un producto que funciona en una demo pero no en el campo. Para un CTO, aparece como requisitos ambiguos, supuestos contradictorios e integraciones difíciles de reproducir.

El bug más caro puede ser una pregunta sin responder

Un equipo puede escribir código excelente y aun así construir algo incorrecto. ¿Qué significa “autorizado”? ¿Qué reloj decide si el acceso está permitido? ¿Qué ocurre si un mensaje llega tarde? ¿“No pasó nada” significa éxito, rechazo, timeout o error interno?

Fred Brooks explicó en No Silver Bullet que la dificultad esencial está en especificar, diseñar y probar el sistema conceptual. La ambigüedad más costosa suele aparecer antes de la primera línea de código.

Una integración real que falló

Probé una integración en tiempo real con hardware edge. Otra aplicación enviaba una solicitud de acceso a un edificio. La política de autorización era compleja y tuvimos que definir mensajes, payloads y secuencias.

Mi prueba local parecía correcta. En la prueba real falló porque existía una regla que no estaba en mi modelo: el dispositivo comprobaba primero la hora. Fuera del horario permitido, no hacía nada.

Ese “nada” no era un mensaje, un error ni una respuesta de autorización. Era ausencia de comportamiento observable. El dispositivo no tenía por qué estar roto; el problema era que nuestra comprensión compartida estaba incompleta.

Más condiciones crean más realidades posibles

El hardware podía operar de cinco formas o más según la hora, el estado del dispositivo, la autorización, la conectividad y el orden de los mensajes. Una prueba local cubre un camino. Producción visita los caminos que nadie escribió.

Los sistemas distribuidos son difíciles por esto: los mensajes se retrasan, duplican, reordenan, rechazan o ignoran. Un payload válido puede ser inválido en el estado actual.

Los principios de Designing Data-Intensive Applications y del libro de SRE de Google apuntan a lo mismo: la fiabilidad, la operación y el fallo deben formar parte del diseño.

La comunicación también es arquitectura

En software, la comunicación no es solo una habilidad blanda: es una dependencia técnica. Cada supuesto no documentado se convierte en una rama oculta. Cada interpretación distinta de “aprobado”, “disponible” o “procesado” se convierte en riesgo de compatibilidad.

La arquitectura también es el acuerdo entre las personas y sistemas responsables de cada parte. Si los equipos no comparten un modelo claro del problema, la arquitectura expone esa brecha.

La IA no elimina la necesidad de claridad

La IA puede ayudar con investigación, implementación, pruebas y documentación. Pero normalmente hace lo que le pedimos. Si el objetivo es incorrecto, las instrucciones son ambiguas o dejamos las decisiones importantes en piloto automático, la IA puede acelerar la dirección equivocada.

No es una razón para evitar la IA. Es una razón para mejorar el sistema que la rodea: definir el resultado, las restricciones, los fallos inaceptables y cuándo debe revisar una persona.

Qué deben hacer explícito los líderes

  • ¿Qué resultado de negocio debe proteger este flujo?
  • ¿Cuáles son los estados y transiciones válidos?
  • ¿Qué condiciones cambian el resultado?
  • ¿Qué significan éxito, rechazo, timeout y fallo?
  • ¿Quién es responsable de cada decisión?
  • ¿Cómo sabrá un operador qué ocurrió?
  • ¿Qué debe ser determinista?

No se trata de eliminar toda incertidumbre. Se trata de decidir dónde es aceptable y dónde es peligrosa. Una recomendación puede ser probabilística; una autorización, un pago o un límite de seguridad normalmente necesita reglas explícitas y observables.

Los retrasos de software suelen ser retrasos de decisión y comunicación disfrazados. Los equipos rápidos no dejan de pensar: resuelven antes las preguntas correctas y conectan el objetivo de negocio con el comportamiento técnico.

La calidad del código importa. Pero antes de que el código pueda ser bueno, el equipo debe acordar qué significa un buen comportamiento.

¿Te ha pasado esto en tu equipo? ¿Una funcionalidad parecía correcta de forma aislada, pero falló cuando entraron en juego el sistema completo, sus reglas ocultas y las condiciones reales? Esa brecha suele ser donde comienza el trabajo de ingeniería más valioso.

I’m Arnold Moya. I write about software architecture, AI, systems, performance, and the tradeoffs behind building technology that works in the real world.