El algoritmo solo consta de tres pasos:
1.- Escribir la especificación del requisito (el ejemplo, el test).
2.- Implementar el código según dicho ejemplo.
3.- Refactorizar para eliminar duplicidad y hacer mejoras.
Otra forma de enumerar los tres pasos es:
1.- Rojo
2.- Verde
3.- Refactorizar
Escribir la especificación
Una vez tenemos claro el requisito, lo expresamos en forma de código.
¿Como se escribe un test para un código que no existe? Un test inicialmente no es un test, sino un ejemplo o especificación.
Un test se puede modificar, no es algo inamovible.
Para escribir el test, tenemos que pensar primero como será la API del elemento a implementar. Solamente una parte pequeña y bien definida. Tenemos que imaginar como seria el código si ya estuviera implementado y como comprobaríamos que hace lo que le pedimos que haga.
Vamos diseñando las especificaciones una a una siguiendo los tres pasos del algoritmo TDD.
Implementar el Código
Con el ejemplo escrito, codificamos lo mínimo necesario para que se cumpla y pase el test.
No importa que el codigo parezca feo o chapucero.
La máxima en este paso es no implementar nada mas que lo estrictamente obligatorio para cumplir la especificación.
Debemos estar concentrados para cumplir esa máxima, ya que siempre escribimos mas codigo del que hace falta.
Si nos vienen a la mente dudas sobre el comportamiento, flujos condicionales que pueden entrar en juego… las anotamos para en siguientes iteraciones retomarlas e implementarlas.
Refactorizar
No significa reescribir el código., refactorizar es modificar el diseño sin alterar su comportamiento, a ser posible sin alterar su API publica.
En este paso:
– Es el momento de detectar malos olores y eliminarlos.
– Rastreamos el código y el test en busca de lineas duplicadas, eliminándolas. Si no existe código duplicado, se consigue uno de más calidad que el que representaba la duplicidad.
– Revisamos que el código cumpla ciertos principios de diseño como SOLID
– Hacer el código más claro y fácil de mantener.
La clave de una buena refactorizacion es hacerlo en pasitos muy pequeños (baby steps)
A cada cambio se ejecutan todos los test, y si sigue funcionando, se hace otro pequeño cambio.
La tarea de refactorizar es la que mas tiende a olvidarse. Es común entrar en la dinámica de escribir el test y luego la implementación y continuar con el siguiente test sin refactorizar.
¿Para que perfil de programador es válido usar TDD?
TDD es valido tanto para desarrolladores expertos como junior.
Un experto será capaz de anticipar futuros casos de uso y futuros problemas y será más cuidadoso diseñando la API test tras test, aplicando las buenas prácticas que conoce.
El junior probablemente se siente a escribir lo que mejor le parece, sin saber que la solución que elige quizás le traiga quebraderos de cabeza más adelante. La ventaja es que, cuando se dé cuenta de que su diseño tiene puntos a mejorar y empiece a refactorizar, contará con un importante respaldo detrás en forma de batería de tests. Por poco experimentado que sea, se cuidará de no diseñar una API que le resulte casi imposible de usar.
Uso de TDD con una nueva tecnología
La primera vez que usamos una determinada tecnología o incluso una nueva librería, no sabemos las limitaciones y fortalezas que ofrece la nueva herramienta.
En Xtreme Programming se habla de spikes.
Un spike es un pequeño programa que se escribe para indagar en la herramienta, explorando su funcionalidad. Es hacerse alguna función o alguna aplicación pequeña que nos aporte el conocimiento que no tenemos.
Sin un conocimiento básico de la API y las restricciones del sistema, no es recomendable lanzarse a escribir especificaciones. Hay que respetar el tiempo de aprendizaje con la herramienta y avanzar una vez que se tenga confianza con ella. Intentar practicar TDD en un entorno desconocido es un antipatrón.
TDD en medio de un proyecto
Para los nuevos requisitos se puede seguir los 3 pasos perfectamente.
Para las partes antiguas que no tienen test de ningún tipo (legacy code), se crean test de sistema, y si el código lo permite, test unitarios, que minimicen los posibles efectos colaterales de la reescritura.
Fuente: Diseño Ágil con TDD