PTENES
MÓDULO 4.3

🪓 Sobreingeniería y deuda técnica generada por IA

Aunque la tasa de errores por línea se mantenga igual, el volumen de código crece y el número total de problemas también. Este módulo trata sobre contener la complejidad antes de que se convierta en estructura.

6
Temas
50
Minutos
Avanzado
Nivel
Práctico
Tipo
0%0 de 6
1

🪓 Exige el cambio mínimo posible

La IA tiende a producir soluciones aparentemente completas, incluso cuando bastaría con una más pequeña: abstracciones prematuras, capas innecesarias, interfaces redundantes, frameworks internos, demasiados archivos, configuración excesiva y manejo de casos hipotéticos.

La regla práctica: pégala en tu AGENTS.md

Implementa el cambio más pequeño que cumpla con los criterios de aceptación.
No crees nuevas abstracciones, dependencias o capas sin una necesidad comprobada.

Dos frases. Es el control con mejor relación costo-beneficio de todo este curso.

✓ misma spec, solución mínima ✗ misma spec, solución inflada 2 archivos 1 prueba nueva 0 dependencias interfaz genérica fábrica + registry capa de config 3 dependencias 18 archivos · "listo para el futuro"

Cómo leer: ambos lados pasan las mismas pruebas. La diferencia se nota de aquí a seis meses, cuando alguien necesite cambiar algo: a la izquierda modifica dos archivos; a la derecha necesita entender la fábrica, el registry y la capa de configuración antes de tocar cualquier línea.

Menor

Que cumpla el criterio

Conservar

La estructura existente

Justificar

Todo componente nuevo

Revisable

Un diff pequeño se lee

2

🏗️ Evita las abstracciones prematuras

Una abstracción equivocada cuesta más que la duplicación: para cambiar cualquier cosa, primero hay que deshacer la abstracción. Y llega con apariencia de calidad: nombres bonitos, capas simétricas, todo «extensible».

✓ Cuándo abstraer

  • ✓Existen dos o tres usos reales, no previstos
  • ✓Los usos varían en el mismo eje (la abstracción captura la variación correcta)
  • ✓La duplicación ya provocó un error de inconsistencia

✗ Cuándo NO abstraer

  • ✗"Algún día vamos a necesitar admitir otro proveedor"
  • ✗Un único uso, con una interfaz creada «por precaución»
  • ✗Semejanza superficial: dos cosas parecidas hoy que evolucionan por separado

💡 Consejo práctico

Pide siempre las dos versiones: "muéstrame la solución simple y la extensible, con el costo de cada una; recomienda una y dime qué se sacrifica". La conversación se vuelve objetiva en treinta segundos, y la respuesta suele ser la simple.

2–3 usos reales

Antes de abstraer

Hipotético

No es un requisito

Incorrecta > duplicada

En costo

Dos versiones

Compara siempre

3

📦 Controla las dependencias y los archivos modificados

Cada dependencia es una superficie de ataque, un costo de actualización y un riesgo de abandono. Y cada archivo adicional en el diff reduce la posibilidad de que alguien lo revise de verdad: a partir de cierto tamaño, el PR no se revisa, se acepta.

🚦 Controles recomendados

  • •Prohibir nuevas dependencias sin aprobación explícita.
  • •Limitar el número de archivos modificados por tarea.
  • •Evita refactorizar fuera del alcance: se convierte en otro PR.
  • •Eliminar el código sin usar que el cambio dejó huérfano.
  • •Evaluar el costo de mantenimiento antes de aceptar la solución.

⚠️ Atención

Una dependencia sugerida por IA merece una revisión adicional: ¿realmente existe? ¿Se mantiene? ¿El nombre es el que esperas? Un paquete inventado —o con un nombre parecido al de uno real— es un vector conocido de ataque a la cadena de suministro.

Costo permanente

Toda dependencia tiene

¿Existe de verdad?

Revisa el paquete

Límite de archivos

Delata el alcance

Huérfano

Elimina lo que quedó

4

👯 Combate la duplicación semántica

Es la forma de deuda que más genera la IA, porque cada tarea empieza sin recordar lo que ya existe. El resultado es la tercera función para formatear fechas, con otro nombre, en otro módulo y con otro comportamiento en los casos límite.

🧪 Ejercicio copiable — cacería de duplicación

Objetivo: medir la deuda semántica acumulada en tu repositorio. Ejecútalo una vez por trimestre.

Analise <pasta ou repositório> e encontre DUPLICAÇÃO SEMÂNTICA: trechos que
resolvem o mesmo problema com implementações diferentes (não copie-e-cola literal).

Para cada grupo encontrado, informe:
- o que fazem (uma frase);
- onde estão (arquivo:linha de cada ocorrência);
- as diferenças de comportamento entre elas (especialmente em bordas:
  nulo, vazio, fuso horário, arredondamento, erro);
- qual é a mais completa e por quê;
- risco de consolidar (baixo/médio/alto).

Não altere nada. Ordene por risco de inconsistência para o usuário final.

Cómo verificar: elige el grupo de mayor riesgo y revisa manualmente las diferencias en los casos límite. Casi siempre hay al menos un caso en el que las dos implementaciones no coinciden; y ese es un bug que nadie había reportado todavía.

"¿Ya existe?"

Pregunta antes de crear

Límites

Dónde discrepan

Inconsistencia

Se convierte en un error para el usuario

Consolidar

Trabajo recurrente

5

🧪 Desconfía de las pruebas superficiales

Una prueba que ejecuta el código sin afirmar un comportamiento relevante ofrece la peor combinación posible: sensación de seguridad sin ninguna protección — y además bloquea refactorizaciones, porque prueba la implementación en vez del comportamiento.

1

La prueba de «romperlo a propósito»

Introduce un bug obvio en la función y ejecuta la suite. Si nada se pone en rojo, esa prueba no prueba nada. Es la forma más rápida de evaluar pruebas generadas por IA.

2

Comportamiento, no implementación

Una prueba que verifica qué métodos internos se llamaron se rompe con cada refactorización y no detecta ningún defecto. Prueba lo que entra y lo que sale.

3

Pide errores y casos límite, no solo el camino feliz

Indica explícitamente: "prioriza casos de error, límites y concurrencia; no generes pruebas redundantes del camino feliz". Sin eso, recibes veinte variaciones del mismo escenario.

Provoca el fallo a propósito

¿La prueba falló?

Comportamiento

Entrada y salida

Límites

Es donde vive el bug

Prueba vacía

Es deuda, no un activo

6

🎭 Detecta el código que viola la intención

Es el defecto más peligroso del desarrollo con IA: la solución que pasa las pruebas y aun así está mal. Pasa por todos los gates automáticos con luz verde, porque se optimizó exactamente para el verificador.

🚩 Señales en el diff

  • • Condición que contempla específicamente el valor usado en la prueba.
  • • try/catch que se traga la excepción y devuelve un valor predeterminado.
  • • Caché agregado «para mejorar el rendimiento» que en realidad oculta la inconsistencia.
  • • Verificación eliminada "porque estaba causando fallas".
  • • Prueba anterior modificada en el mismo commit de la corrección.

Verificación rápida: el agente entregó 18 archivos, 3 dependencias nuevas y una capa de abstracción, y todo pasa. ¿Qué hacer?

Leer el diff

No solo el resultado

Excepción descartada

Bandera roja

Prueba modificada

Junto con la corrección

Métrica objetivo

Deja de medir

📌 Resumen del módulo

✓
El cambio más pequeño posible - dos frases en AGENTS.md que equivalen a todo un proceso.
✓
Abstracción después del uso real - la equivocada cuesta más que la duplicación.
✓
Dependencia y diff dentro del límite - y comprueba si el paquete sugerido realmente existe.
✓
Duplicación semántica - la deuda típica de la IA; búscala cada trimestre.
✓
Una prueba que no falla no prueba nada - rómpelo a propósito para comprobar.
✓
Pasar ≠ estar correcto - la violación de intención supera todos los gates.

Próxima ruta:

Ruta 5 - Playbooks, Skills, Rules y gobernanza: transformar todo esto en un proceso reutilizable.