• 10 hours
  • Medium

Free online content available in this course.

course.header.alt.is_video

course.header.alt.is_certifying

Got it!

Last updated on 8/6/19

Stop on the right exception

Make use of the Test Explorer panel

 For the scenario where a test fails because of an unexpected exception, start with the Test Explorer panel. To access it, go into the TEST | Windows | Test Explorer menu:

Menu for going into Test Explorer
Menu for getting into Test Explorer

Select the VerifyAddTasks test, and run it by right-clicking Run Selected Tests:

Start the VerifyAddTasks test
Start the VerifyAddTasks test

Visual Studio’s Test Explorer panel results window provides a minimum of information to help you understand the cause of the test failure:

Failure in executing a unit test
Failure in executing a unit test

In the first instance, the failure comes from an exception thrown by the code (red box).

Next, the details of the exception in question are presented (green box):

  • Its type (here, an ArgumentNullException).

  • And message Value cannot be null.

What does this information give you?

The exception type, along with the message, indicates that a method has received an unsupported null value parameter. You need to determine which method this is, and who sent it a null. Note that the name of this parameter is given just below: source. This corresponds to the enumeration from which FirstOrDefault is called.

You can find part of the answer in the StackTrace section: the stack of method calls are displayed from the last one before the exception, up to the unit test (blue box).

Configure exception handling

Let’s get back to our investigation. Unfortunately, it’s too late to resolve the issue. :o

In fact, we should have asked the debugger to stop the execution at the exact place in the code where the exception was thrown and not when the test had failed.

To do this, you use the DEBUG | Windows | Exception Settings menu:

Exception Settings menu
Exception Settings menu

The panel that appears lists all the exception types that can be thrown:

Exceptions configuration panel
Exceptions configuration panel

We’re only interested in those thrown in the .NET context, which appears in the Common Language Runtime Exceptions section. If you check the box alongside an exception (in our case, ArgumentNullException), the debugger will suspend execution, and the editor will show the instruction that throws the exception.

To make this behavior possible, this time run the test from the Debug command (instead of Run):

Debugging a unit test
Debugging a unit test

This means that the code will be run under the control of Visual Studio’s debugger.

The debugger will stop on the line of code that throws the exception. In our case, the call to the FirstOrDefault method:

Execution paused on an exception
Execution paused on an exception

The line in question is highlighted in the code editor, and a little box gives the details of the exception, like its message.

As you’re not familiar with the unit test code or the methods called there, it can be difficult to understand what's going on, and where you are in the execution. Fortunately, the call stack is automatically displayed in the Call Stack panel when the exception is detected. This enables you to understand where you are in the execution:Call stack panel

Call Stack panel

The exception occurred in the method at the top of the stack marked with the curved arrow, TodoModel.GetTask. It has appeared automatically in the Visual Studio code editor.

The next method in the stack, TodoModel.InternalAddTask corresponds to the one that called it. This way, you can go back until you know at where you are in the test. To do this, go down as far as the T_TodoModel method, and double-click on the line VerifyAddTasks (highlighted in blue on the previous screenshot):

Call stack for VerifyAddTasks
Call stack for VerifyAddTasks

The little curved arrow appears in both the call stack and the method code to indicate the instruction corresponding to the call to the TodoModel.CreateTask method, i.e., the line above in the call stack:

Execution at the level of CreateTask
Execution at the level of CreateTask

These selections enable you to find the sequence of method calls that resulted in the exception.

Going back to our investigation, the _tasks collection on which FirstOrDefault is called, seems not to be initialized. It would be interesting to find out the taskName value for which the exception was thrown. To do this, hover the mouse over it, and its value will be displayed directly in the editor – in our case, “sleep”:

TaskName value
TaskName value

We will go over the various means of viewing and modifying the values of the parameters and fields in data structures in more detail in the last chapter.

Let's recap!

You’ve just seen how to ask the debugger to stop as soon as an exception is thrown. You also saw the execution sequence for the methods using the Call Stack panel.

The question now is knowing how to ask the debugger to stop, not at the moment the exception is thrown, but at the place in the unit test that will lead to the error. It will then be possible to find the status of the local variables for each method, together with the values of the various parameters used in the successive calls.

The answer is in the next chapter! 😁

Example of certificate of achievement
Example of certificate of achievement