I'm testing a method that manipulates a collection. Given a set of parameters it should contain exactly one element that matches a condition. Edit: The collection might have several other elements not matching the condition aswell.
I'm using Single to test that behaviour, which works fine, as it will fail the test by throwing an exception if there is no match at all or more than one match. But there is no actual assert, which somehow violates arrange, act, assert. So I'm wondering if this is a bad practice and if there's a better way to do this.
Following pseudo code to demonstrate my question:
[TestMethod]
public void TestMethod()
{
List list = MethodToTest(param1, param2);
list.Single(s => s.Matches(condition));
//No actual Assert
}
Assertions will help only during internal testing to catch failure of assumptions. You should not assume the behavior of external agencies, so you should not assert on events from the network or user. Also it is a good practice to write handling code for production builds in case an assertion fails.
“One assertion per test” is a wise rule to keep in mind, because it helps you have tests that fail for a specific reason, and drives you to focus on a specific behavior at a time.
The so-called “single assert rule” simply means that a test should be a single state transition. Arrange, act, assert.
Multiple asserts occur when you use more than one assert statement in a single unit test. This is bad when you use multiple assert statements to check various scenarios and make the test function more complicated to read and maintain.
I'm wondering if this is a bad practice and if there's a better way to do this.
Yes and yes.
it will fail the test by throwing an exception if there is no match at all or more than one match.
Don't fail the test by throwing an exception. Fail the test by failing the test. Your test framework has a mechanism for asserting the condition being tested by the test. You bought this test framework, and now you are resisting using its features. Use the test framework as it was designed to be used, or, if you don't like it, abandon it and choose a framework you like better. But don't do end-runs around its mechanisms.
Unexpected exceptions are not necessarily test failures; they could be buggy tests. You need to be able to tell the difference. The way you tell is: if the exception originates in the code under test, its a bug in the code. If it originates in the test code, its a bug in the test. And now you go and detect a bug in the code under test by making the testing code throw. And now it is harder to tell where the bug is. Don't make your future self think that hard; don't write surprising code that deliberately avoids the conventions of the testing platform.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With