c# - test - NUnit 3.0 y Assert.Throws
unit test c# ejemplo (3)
Estoy escribiendo algunas pruebas unitarias con NUnit 3.0 y, a diferencia de v2.x,
ExpectedException()
se ha eliminado de la biblioteca.
Con base en this respuesta, definitivamente puedo ver la lógica al tratar de detectar específicamente en qué parte de la prueba se espera que su sistema arroje una excepción (en lugar de decir ''en cualquier parte de la prueba'').
Sin embargo, tiendo a ser muy explícito sobre mis pasos Organizar, Actuar y Afirmar y esto lo convierte en un desafío.
Solía hacer algo como:
[Test, ExpectedException(typeof(FormatException))]
public void Should_not_convert_from_prinergy_date_time_sample1()
{
//Arrange
string testDate = "20121123120122";
//Act
testDate.FromPrinergyDateTime();
//Assert
Assert.Fail("FromPrinergyDateTime should throw an exception parsing invalid input.");
}
Ahora necesito hacer algo como:
[Test]
public void Should_not_convert_from_prinergy_date_time_sample2()
{
//Arrange
string testDate = "20121123120122";
//Act/Assert
Assert.Throws<FormatException>(() => testDate.FromPrinergyDateTime());
}
Esto no es terrible, pero enturbia la Ley y la Afirmación, en mi opinión. (Obviamente, para esta prueba simple, no es difícil de seguir, pero podría ser más difícil en pruebas más grandes).
Un colega me sugirió que me deshiciera de
Assert.Throws
completo y simplemente hace algo como:
[Test]
public void Should_not_convert_from_prinergy_date_time_sample3()
{
//Arrange
int exceptions = 0;
string testDate = "20121123120122";
//Act
try
{
testDate.FromPrinergyDateTime();
}
catch (FormatException) { exceptions++;}
//Assert
Assert.AreEqual(1, exceptions);
}
Aquí, me quedo con el estricto formato AAA, pero a expensas de aún más hinchazón.
Entonces, mi pregunta se dirige a los evaluadores de estilo AAA: ¿cómo harían algún tipo de prueba de validación de excepción como estoy tratando de hacer aquí?
En C # 7, hay otra opción (aunque muy similar a las respuestas existentes):
[Test]
public void Should_not_convert_from_prinergy_date_time_sample2()
{
void CheckFunction()
{
//Arrange
string testDate = "20121123120122";
//Act
testDate.FromPrinergyDateTime();
}
//Assert
Assert.Throws(typeof(Exception), CheckFunction);
}
Puede crear un Atributo personalizado en NUnit 3. Aquí está el código de muestra de cómo crear el Atributo [ExpectedException]. (ExpectedExceptionExample Muestra cómo implementar un atributo personalizado para NUnit) https://github.com/nunit/nunit-csharp-samples
Veo de dónde vienes, aunque no me importa combinar los pasos Act / Assert en este caso.
Lo único que se me ocurre es almacenar el delegado real (aquí para
FromPrinergyDateTime
) en una variable como el paso "actuar" y luego afirmarlo:
[Test]
public void Should_not_convert_from_prinergy_date_time_sample2()
{
//Arrange
string testDate = "20121123120122";
//Act
ActualValueDelegate<object> testDelegate = () => testDate.FromPrinergyDateTime();
//Assert
Assert.That(testDelegate, Throws.TypeOf<FormatException>());
}
Entiendo que el paso "actuar" no es realmente actuar, sino definir qué es la acción. Sin embargo, define claramente qué acción se está probando.