Python unittest assertraises allows you to verify that a certain exception is raised when your code is run. Python’s unittest module provides a set of tools for testing your code. Note that the Python unittest assertRaises function does not call the exceptions __init__ method. It can be used to test both your code and code from third-party libraries.
Contents
How to Use Python Unittest Assertraises
To use Python unittest assertRaises
, you pass
in the exception, you expect to be raised as well as a callable
that will execute the code you want to test. assertRaises
will then automatically verify that the correct exception is raised.
In this article, we’ll take a closer look at how to use the assertRaises
method, with some practical examples.
Parameters
assertRaises(exception, callable, *args, **kwds)
exception
– Exception class expected to be raised bycallable
.callable
– Function to be called. Astring
identifying a callable object may also be supplied. Thecallable
will be invoked withargs
andkwds
as appropriate.*args
– Positional arguments passed tocallable
when invoked.**kwds
– Keyword arguments passed tocallable
when invoked.
Returns:
Returns
: The return value from calling callable
(or None
if an exception is not raised).
Basic usage
Example – 1
Let’s start with a very simple example for Python unittest assertraises. We have a function that raises a ValueError
if the input value is negative:
def raise_if_negative(value):
if value < 0:
raise ValueError('Value cannot be negative')
We can write a test for this using assertRaises
:
import unittest
class TestRaiseIfNegative(unittest.TestCase):
def test_raise_if_negative(self):
with self.assertRaises(ValueError):
raise_if_negative(-1)
The with
the statement is used here to create a context manager. This allows us to write the test in a more “Pythonic” way, without having to explicitly call the assertRaises method. The advantage of this approach is that it makes the text more readable and easier to maintain.
Let’s see another example:
Example – 2
We have a function that converts a string to uppercase, but it fails if the input string is empty:
def to_upper(value):
if not value:
raise ValueError('Value cannot be empty')
return value.upper()
We can write a test for this using assertRaises
:
import unittest
class TestToUpper(unittest.TestCase):
def test_to_upper(self):
with self.assertRaises(ValueError):
to_upper('')
If you run this test, you’ll see that it fails with the following error message:
AssertionError: ValueError not raised by to_upper
Wait, what?
How can this be? We clearly defined a ValueError
in our function, so why is the test failing?
The reason is that the assertRaises
method only catches exceptions that are raised in the with block. In our case, the to_upper
function is never called, so the exception is never raised.
To fix this, we can explicitly call the function inside the with
block:
import unittest
class TestToUpper(unittest.TestCase):
def test_to_upper(self):
with self.assertRaises(ValueError):
to_upper('')
Now if you run the test, it passes:
PASSED
If you want to be able to call the function outside of the with
block, you can store it in a variable:
import unittest
class TestToUpper(unittest.TestCase):
def test_to_upper(self):
to_upper_fn = to_upper('')
with self.assertRaises(ValueError):
to_upper_fn()
Verifying the Exception Message
In the previous section, we saw how to verify that a certain code path is reached when an exception is raised. But sometimes it’s also important to verify the exception message.
The assertRaises
method allows us to do this by passing it an additional argument: a function that receives the raised exception as an argument and verifies its contents.
Let’s see how this works with our example from the previous section:
import unittest
def test_to_upper(self):
with self.assertRaises(ValueError):
to_upper('')
If we run this test, it fails:
AssertionError: ValueError not raised by to_upper
To fix this, we can pass a function that verifies the exception message:
import unittest
def test_to_upper(self):
with self.assertRaises(ValueError) as cm:
to_upper('')
self.assertEqual(str(cm.exception), 'Value cannot be empty')
The assertEqual
method is used here to verify that the exception message is equal to the expected message.
If you run the test now, it passes:
Verifying the Exception Type
In addition to verifying the exception message, there are also cases where you need to verify the exception type. For example, you might have a function that can raise either a ValueError
or an AttributeError
, and you want to verify that only a ValueError
is raised:
def do_something(value):
if value == 'a':
raise ValueError('Invalid value')
elif value == 'b':
raise AttributeError('Invalid value')
In this case, we can use the assertRaises
the method with multiple arguments:
import unittest
def test_do_something(self):
with self.assertRaises(ValueError):
do_something('a')
with self.assertRaises(AttributeError):
do_something('b')
If we try to call do_something
with a value that doesn’t raise any exception, the test fails:
AssertionError: AttributeError not raised by do_something
To fix this, we can add a third with
block that verifies that no exception is raised:
import unittest
def test_do_something(self):
with self.assertRaises(ValueError):
do_something('a')
with self.assertRaises(AttributeError):
do_something('b')
with self.assertRaises(Exception): # any exception
do_something('c')
If you run the test now, it passes:
PASSED
Conclusion
In this article, we’ve seen how to use Python unittest assertRaises
method to write tests that verify that a certain code path is reached when an exception is raised. We’ve also seen how to use this method to verify the exception message and type.
Keep in mind that the assertRaises
method can only be used with exceptions that are raised in the with
block. This means that you might need to explicitly call the function that raises the exception, as we saw in the examples above.
References
- Daniel Perez – assertRaises in Python | Published on Oct 22, 2017
- Python Documentation
- StackOverflow
- TutorialsPoint – UnitTest Framework – Exceptions Test
That’s all for this post. To be up to date with our latest posts follow Python Clear. Let’s learn together!