Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

integrate with coveragepy 5 who-tests-what feature: @pytest.mark.covers #377

Open
graingert opened this issue Jan 6, 2020 · 0 comments
Open

Comments

@graingert
Copy link
Member

graingert commented Jan 6, 2020

Coveragepy 5 now supports coverage provenance in a "who-tests-what" feature. Currently this information is reported on but there's currently no easy way to provide assertions on the information

I'd like to be able to mark modules and classes with @pytest.mark.covers('path.to.some.sut', fail_under=...)

And have them a test suite fail if the coverage by the items contained in the node hierarchy are not sufficient to cover 'path.to.some.sut'

Design

Scope Grouping

The scope of the mark effects the grouping of the coverage assertion:

# testing/ham/spam/selenium.py
import pytest

from ham import spam
pytestmark = pytest.mark.covers(spam.__spec__.name)


def test_baz(browser): ...

@pytest.mark.covers(spam.eggs.__qualname__)
class TestEggs:
    def test_foo(self, browser): ...
    def test_bar(self, browser): ...

testing.ham.spam.selenium.test_baz, testing.ham.spam.selenium.TestEggs.test_foo and testing.ham.spam.selenium.TestEggs.test_bar should cover "ham.spam" completely on their own

testing.ham.spam.selenium.TestEggs.test_foo and testing.ham.spam.seleniumTestEggs.test_bar should cover ham.spam.eggs completely on their own - regardless of if testing.ham.spam.selenium.test_baz
happens to cover any of "ham.spam.eggs" or any other test in the suite happens to do so.

A new file

adding a new file, should not weaken any of the above coverage assertions:

# testing/ham/spam/unit.py
import pytest

from ham import spam
pytestmark = pytest.mark.covers(spam.__spec__.name)


def test_baz(db): ...

@pytest.mark.covers(spam.eggs.__qualname__)
class TestEggs:
    def test_foo(self, db): ...
    def test_bar(self, db): ...

In addition:
testing.ham.spam.unit.test_baz, testing.ham.spam.selenium.unit.test_foo and testing.ham.spam.unit.TestEggs.test_bar should cover "ham.spam" completely on their own

testing.ham.spam.unit.TestEggs.test_foo and testing.ham.spam.unit.test_bar should cover ham.spam.eggs completely on their own - regardless of if testing.ham.spam.unit.test_baz or any other test in the suite
happens to cover any of "ham.spam.eggs"

Grouping override

an groupe kwarg allows you to explicitly weaken the coverage assertion:

# testing/ham/eggs/selenium/marks.py
import pytest
from ham import eggs
covers_spam_together = pytest.mark.covers(eggs.__spec__.name, group=__spec__.name)
# testing/ham/eggs/selenium/homepage.py
from .marks import helpers

pytestmark = helpers.covers_spam_together
# testing/ham/eggs/selenium/cart.py
from .marks import helpers

pytestmark = helpers.covers_spam_together

Problems

I'm not particularly happy with my design for explicit grouping. Would sentinel objects be better?

UNIT = object()
SELENIUM = object()
covers_spam_unit = pytest.mark.covers(eggs.__spec__.name, group=UNIT)
covers_spam_selenium = pytest.mark.covers(eggs.__spec__.name, group=SELENIUM)

can mark instances themselves be a sentinel by default?

covers_spam_selenium = pytest.mark.covers(eggs.__spec__.name)
covers_spam_selenium = pytest.mark.covers(eggs.__spec__.name)

would it be better to disable scope-grouping entirely, and require a group kwarg?
this could result in spooky-action-at-a-distance in which adding testing.ham.spam.unit to a suite implicitly weakens testing.ham.spam.selenium

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant