Skip to content

RFC: parametrizing conditional raising with pytest.raises #1830

Closed
@The-Compiler

Description

@The-Compiler

Currently, parametrizing conditional raising of an exception is rather
cumbersome. Consider this:

def foo(inp):
    if inp:
        raise ValueError("Just a silly example")

When we write a test for it, we need to repeat ourselves:

@pytest.mark.parametrize('inp, raising', [(True, True), (False, False)])
def test_foo(raising):
    if raising:
        with pytest.raises(ValueError):
           foo(inp)
    else:
        foo(inp)

An easy way to solve this would be to add something like an activated
argument to pytest.raises, where it simply does nothing:

@pytest.mark.parametrize('inp, raising', [(True, True), (False, False)])
def test_foo(inp, raising):
    with pytest.raises(FooError, activated=raising):
        foo(inp)

But then sometimes, it's handy to parametrize the exception too - consider
this:

def bar(inp):
    if inp == 1:
        raise ValueError
    elif inp == 2:
        raise TypeError
    else:
        pass

and the test:

@pytest.mark.parametrize('inp, exception', [(1, ValueError), (2, TypeError),
                                            (3, None)])
def test_bar(inp, exception):
    if exception is None:
        bar(inp)
    else:
        with pytest.raises(exception):
            bar(inp)

So maybe we could just use None as a special value where pytest.raises does
nothing?

@pytest.mark.parametrize('inp, exception', [(1, ValueError), (2, TypeError),
                                            (3, None)])
def test_bar(inp, exception):
    with pytest.raises(exception):
        bar(inp)

Or if we're worried about None being accidentally used (though I'm not sure
how?), we could use a special value, potentially pytest.raises.nothing or so
😆

Opinions?

Metadata

Metadata

Assignees

No one assigned

    Labels

    type: enhancementnew feature or API change, should be merged into features branchtype: proposalproposal for a new feature, often to gather opinions or design the API around the new feature

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions