views:

2176

answers:

2

How do I use Assert.Throws to assert type of the exception and the actual message workding.

Something like this:

Assert.Throws<Exception>(
    ()=>user.MakeUserActive()).WithMessage("Actual exception message")

Method I am testing throws multiple messages of the same type, with different message and I need a way to test that correct message is thrown depending on the context.

+18  A: 

Assert.Throws returns the exception that's thrown which lets you assert on the exception.

var ex = Assert.Throws<Exception>(() => user.MakeUserActive());
Assert.That(ex.Message, Is.EqualTo("Actual exception message"));

So if no exception is thrown, or an exception of the wrong type is thrown, the first (Assert.Throws) assertion will fail. However if an exception of the correct type is thrown then you can now assert on the actual exception that you've saved in the variable.

By using this pattern you can assert on other things than the exception message to, for example in the case of ArgumentException and derivatives you can assert that the parameter name is correct:

var ex = Assert.Throws<ArgumentNullException>(() => foo.Bar(null));
Assert.That(ex.ParamName, Is.EqualTo("bar"));

You can also use the fluent api for doing these asserts:

Assert.That(() => foo.Bar(null), 
Throws.Exception.TypeOf<ArgumentNullException>().With.Property("ParamName").EqualTo("bar"));

A little tip when asserting on exception messages is to decorate the test method with the SetCultureAttribute to make sure that the thrown message is using the expected culture. This comes into play if you store your exception messages as resources to allow for localization.

Patrik Hägne
A: 

You should take a look at Visual T#: a programming language specialized for unit testing.

It would be as simple as :

assert thrown ArgumentNullException;

for a simple exception check and

assert thrown ArgumentNullException ex {
  assert ex.Message == "Actual exception message"
}

for your sample.

It is a lot more understandable than NUnit syntax!

Ludovic Dubois
"It is a lot more understandable than NUnit syntax!" Isn't that a bit subjective?
Patrik Hägne
From someone who is new to unit testing frameworks it isn't the syntax the confuses me, it is keeping the test simple enough to make sense -- so methodology is the problem for me.
Richard Slater
-1 for pimping your own product without explicitly stating this.
Andy_Vulhop