Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Why does mypy raise truthy-function error for assertion?

I inherited a project from a dev who is no longer at the company.
He wrote this test:

from contextlib import nullcontext as does_not_raise


def test_validation_raised_no_error_when_validation_succeeds():
    # given
    given_df = DataFrame(data={"foo": [1, 2], "bar": ["a", "b"]})
    given_schema = Schema(
        [
            Column("foo", [InListValidation([1, 2])]),
            Column("bar", [InListValidation(["a", "b"])]),
        ]
    )
    # when
    _validate_schema(given_df, given_schema)

    # then
    assert does_not_raise  # line 251

This project has mypy configured and it complains about the assertion:

test/clients/test_my_client.py:251: error: Function "Type[nullcontext[Any]]" could always be true in boolean context  [truthy-function]
Found 1 error in 1 file (checked 24 source files)

I don’t understand what the problem is.
The documentation doesn’t provide any meaningful advice.
I can disable the check like this:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

assert does_not_raise  # type: ignore

but I’d rather understand the problem and address it properly.

For reference, here is the mypy config:

[mypy]
python_version = 3.8
warn_return_any = True
warn_unused_configs = True
ignore_missing_imports = True

>Solution :

The test intends to check that the # given and # when parts of the test case run without raising any exception. The # then part is probably only there to satisfy the given-when-then pattern. As mypy says, the line doesn’t do anything, it is functionally equivalent to assert bool(some_existing_function_name) which is equivalent to assert True, which is functionally equivalent to just having a comment.

Note that does_not_raise is a function, but it’s not called. Just naming a function in an assert (or if) always returns True.

You can keep silencing the mypy warning as you do now, replace it with assert True, assert "if this line runs, the previous parts didn't raise any exception", or just a comment – they will all be functionally equivalent.

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading