unit-testing
Pruebas Unitarias: Mejores Prácticas
Buscar..
Introducción
Una prueba de unidad es la parte comprobable más pequeña de una aplicación, como funciones, clases, procedimientos, interfaces. La prueba de unidad es un método mediante el cual se prueban las unidades individuales del código fuente para determinar si son aptas para el uso. Los desarrolladores de software básicamente escriben y ejecutan las pruebas unitarias para asegurarse de que el código cumple con su diseño y sus requisitos y se comporta como se espera.
Buen nombramiento
La importancia de un buen nombramiento, puede ilustrarse mejor con algunos malos ejemplos:
[Test]
Test1() {...} //Cryptic name - absolutely no information
[Test]
TestFoo() {...} //Name of the function - and where can I find the expected behaviour?
[Test]
TestTFSid567843() {...} //Huh? You want me to lookup the context in the database?
Las buenas pruebas necesitan buenos nombres. Buena prueba no prueba métodos, los escenarios de prueba o requisitos.
La buena denominación también proporciona información sobre el contexto y el comportamiento esperado. Idealmente, cuando la prueba falla en su máquina de compilación, debería poder decidir qué está mal, sin mirar el código de prueba, o incluso más difícil, tener la necesidad de depurarlo.
Una buena asignación de nombres le ahorra tiempo para leer el código y depurar:
[Test]
public void GetOption_WithUnkownOption_ReturnsEmptyString() {...}
[Test]
public void GetOption_WithUnknownEmptyOption_ReturnsEmptyString() {...}
Para los principiantes, puede ser útil comenzar el nombre de la prueba con un prefijo Aseguramiento o similar. Comience con un "Garantía de que_" ayuda a comenzar a pensar en el escenario o requisito, que necesita una prueba:
[Test]
public void EnsureThat_GetOption_WithUnkownOption_ReturnsEmptyString() {...}
[Test]
public void EnsureThat_GetOption_WithUnknownEmptyOption_ReturnsEmptyString() {...}
El nombramiento es importante para los accesorios de prueba también. Nombre el dispositivo de prueba después de la clase que se está probando:
[TestFixture]
public class OptionsTests //tests for class Options
{
...
}
La conclusión final es:
La buena denominación conduce a buenas pruebas que conducen a un buen diseño en el código de producción.
De lo simple a lo complejo.
Igual que con las clases de escritura: comience con los casos simples, luego agregue el requisito (también conocido como pruebas) y la implementación (también conocido como código de producción) caso por caso:
[Test]
public void EnsureThat_IsLeapYearIfDecimalMultipleOf4() {...}
[Test]
public void EnsureThat_IsNOTLeapYearIfDecimalMultipleOf100 {...}
[Test]
public void EnsureThat_IsLeapYearIfDecimalMultipleOf400 {...}
No olvide el paso de refactorización, cuando haya terminado con los requisitos: primero refactorice el código, luego refactorice las pruebas
Cuando termine, debe tener una documentación completa, actualizada y LECTURA de su clase.
Concepto de MakeSut
Testcode tiene las mismas exigencias de calidad que el código de producción. MakeSut ()
- mejora la legibilidad
- puede ser fácilmente refaccionado
- perfectamente compatible con la inyección de dependencia.
Aquí está el concepto:
[Test]
public void TestSomething()
{
var sut = MakeSut();
string result = sut.Do();
Assert.AreEqual("expected result", result);
}
El MakeSut () más simple simplemente devuelve la clase probada:
private ClassUnderTest MakeSUT()
{
return new ClassUnderTest();
}
Cuando se necesitan dependencias, se pueden inyectar aquí:
private ScriptHandler MakeSut(ICompiler compiler = null, ILogger logger = null, string scriptName="", string[] args = null)
{
//default dependencies can be created here
logger = logger ?? MockRepository.GenerateStub<ILogger>();
...
}
Se podría decir que MakeSut es solo una alternativa simple para los métodos de configuración y desmontaje proporcionados por los marcos de prueba de Testrunner y podría considerar estos métodos como un mejor lugar para realizar una configuración y desmontaje específicos de prueba.
Todos pueden decidir por su cuenta, qué forma de usar. Para mí, MakeSut () proporciona una mejor legibilidad y mucha más flexibilidad. Por último, pero no menos importante, el concepto es independiente de cualquier marco de ejecución de pruebas.