2009-02-03 9 views
5

Personalmente, siempre he puesto las pruebas unitarias en un proyecto separado simplemente porque así es como parece que MSTest está configurado. Pero estoy leyendo Refactoring: Mejorando el Diseño del Código Existente por Martin Fowler y él parece estar abogando no solo por ponerlos en el mismo proyecto, sino también por ponerlos en la misma clase que el método que están probando.¿Cuáles son las ventajas del código de autoevaluación frente a las pruebas separadas?

Realmente, estoy teniendo problemas para pensar en la forma en que esto es diferente de tener las pruebas en un área separada del código en sí que no sean diferencias filosóficas (¿la documentación de las pruebas o el desorden?).

¿Existen razones claras para elegir una sobre otra? ¿O es principalmente una diferencia filosófica?

ACTUALIZACIÓN: No estoy necesariamente convencido de una u otra manera, pero al menos tengo una idea de cuáles son los argumentos. Ojalá pudiera seleccionar la respuesta de todos, pero tuve que seleccionar solo uno.

Respuesta

5

Tal vez haya algo de elegancia en tener códigos de autodiagnóstico, pero tiendo a estar del lado de la misma filosofía que usted: esa separación de códigos sobrepasa alguna noción de belleza abstracta. Cuando se diseña una clase, puede romper fundamentalmente en tres partes:

  • Lo que hace la clase (por ejemplo, la definición de clase)
  • cómo lo hace (la aplicación)
  • La forma de utilizar (casos de documentación y/o pruebas)

Considero que los casos de prueba cumplen la función de documentación, así como parte de una red de seguridad en un banco de pruebas. Cuando un nuevo programador está mirando su código, posiblemente mucho después de que haya dejado de trabajar en él, la documentación rara vez es la forma más efectiva de comunicar cómo debe usarse la clase. Puede responder preguntas sobre cómo se comporta el código en situaciones específicas, proporcionando una descripción general de la clase y sus métodos, etc., pero los casos de prueba proporcionan un ejemplo concreto de cómo se usaría la clase en código real.

Así que por esa razón, tendería a decir que deberían permanecer fuera de la clase en sí, ya que esto refuerza este grado de separación.

1

Creo que es principalmente una diferencia filosófica.

Puede haber ventajas de rendimiento marginal al tenerlos en un proyecto separado (en la medida en que sus pruebas no se implementan en la producción), pero probablemente no son que significativo.

También recuerde que Refactoring se escribió hace bastante tiempo (en términos de TI) por lo que las prácticas preferidas pueden haber cambiado desde entonces.

4

Ponerlos en la misma clase que se está probando puede romper los marcos de prueba de unidades populares, ya que NUnit no probará los tipos que no tienen un constructor sin parámetros predeterminado.

Poner las pruebas en un archivo diferente, pero el mismo proyecto es mejor, pero aún hace que su proyecto principal haga referencia a marcos de prueba como NUnit.Framework.dll, así como a marcos de referencia como Rhino.Mocks.dll.

Tener sus pruebas dentro de la clase bajo prueba también aumenta el tamaño de su proyecto distribuido.

Separe las pruebas en un proyecto separado, y no tiene ninguno de estos problemas.

3

Mantener sus pruebas en un área separada (subdirectorio, proyecto, lo que sea) es una buena manera de conservar la opción de implementar solo el código de producción, que generalmente es lo que usted querrá hacer.

2

Hay muchas conveniencias en tener sus pruebas en la misma clase que está probando. Muy a menudo (y antes de embarcar en TDD), utilicé agregar un método principal a la clase solo para probar la funcionalidad del código que escribí. Y no eliminé el método principal porque era bastante útil tener el código de prueba por ahí. Esto fue conveniente, en el mismo sentido en que es conveniente tener documentación vinculada a su código. No tuve que buscar en otro lado ni buscar el código de prueba.

Habiendo dicho eso, el objetivo de TDD no se trata solo de probar/garantizar la calidad. Se trata más de hacer que pienses sobre tu diseño/interfaces. Y desde ese punto de vista, tiene sentido tener su código de "prueba" (a.k.a "design") en un archivo separado. Su código de "prueba" es el cliente/usuario de su clase.

Si el propósito de escribir pruebas en un archivo separado fue técnico, es decir "porque el marco de pruebas unitarias fue diseñado de esa manera" o "de lo contrario tendrá que incluir una referencia en su proyecto principal" o " mejora el rendimiento ", eso no suena muy convincente. Si ese fuera el caso, las cosas se habrían hecho de manera muy diferente.

2

No veo ningún beneficio en tener código de prueba y código de producción en la misma clase. En cambio veo algunas desventajas:

  • No será posible implementar y distribuir el código de producción sin el código de prueba. Por lo tanto, en lugar de un archivo de 100 KB, es posible que deba enviar un archivo de 200 KB o superior. (Cuando se usa TDD, las líneas de código de prueba suelen ser iguales o mayores a las líneas de código de producción).

  • La estructura de las pruebas está unida al código de producción. No debe haber relación 1: 1 entre las pruebas y las clases de producción. En cambio, debe haber una relación 1: 1 entre las pruebas y el comportamiento.

citado de http://blog.daveastels.com/files/BDD_Intro.pdf

"Cuando se da cuenta que se trata de especificar el comportamiento y no escribir pruebas, su punto de vista se desplaza. De repente, la idea de tener una clase de prueba para cada uno de su producción las clases son ridículamente limitantes. Y la idea de probar cada uno de tus métodos con su propio método de prueba (en una relación de 1-1) será risible ".

Programa principalmente en Java y utilizo Maven para construir mis proyectos. Ahí tengo las pruebas en el mismo módulo y paquete que las clases de producción en las que operan, pero en un directorio diferente (/ src/main/java y/src/test/java). Cuando Maven construye el proyecto, ejecuta todas las pruebas, pero solo el código de producción se incluye en la distribución binaria.

Cuestiones relacionadas