Skip to main content

pytest style fixtures outside pytest

Project description

py-fixture

Documentation Status

pytest style fixtures

Features:

  • fixture decorator to mark function as fixture factory
  • Fixture Scope - unit of work for fixture value evaluation
  • Fixture Context - Fixture Scope is also a context manager
  • Value Cache - Fixture value is evaluated only once per scope
  • Fixture Factory Argument Replacement - Invoke fixture factory with replaced arguments
  • Generator Fixture - Generator function could be used as fixture factory
  • Scope tear down - through .finish() method. Individual fixtures are torn down in reverse order of their evaluation
  • Generator fixture tear down
  • Detect recursive evaluation

Examples

Basic Example

This basic example demonstrates the fixture decorator, fixture scope and value cache.

from pyfixture import fixture, FixtureScope
@fixture
def x():
    print("Evaluate x")
    return 1

scope = FixtureScope()
scope.get_fixture_value('x')
# Evaluate x
# 1
scope.get_fixture_value('x')
# 1

Advanced Example

This example build on the basic example by demostrating additional features:

  • Fixture factory argument replacement
  • Fixture Context - fixture scope using context manager
  • Generator fixture
  • Scope tear down
  • Generator fixture tear down
from pyfixture import fixture, FixtureScope

@fixture
def x():
    print("Evaluate x")
    yield 1
    print("Tear down x")

@fixture
def y():
    print("Evaluate y")
    yield 2
    print("Tear down y")

@fixture
def z(x, y):
    print("Evaluate z")
    yield x + y
    print("Tear down z")

def i_am_not_fixture(a, x, y, z):
    print(f"i_am_not_function: a: {a}, x: {x}, y:{y}, z:{z}")

with FixtureScope() as scope:
    print("Get z for the first time")
    assert scope.get_fixture_value("z") == 3
    print("Get z for the second time")
    assert scope.get_fixture_value("z") == 3
    print("Bind a function")
    binded = scope.bind(i_am_not_fixture, ignore_missing=True)
    binded(200)
    print("Finish scope")
# Get z for the first time
# Evaluate x
# Evaluate y
# Evaluate z
# Get z for the second time
# Bind a function
# i_am_not_function: a:200, x: 1, y:2, z:3
# Finish scope
# Tear down z
# Tear down y
# Tear down x

Fixtures can have other fixtures as parameters. Parameters are evaluated and replaced automatcally:

@fixture
def theta(z):
    print("Theta: {z}")
    return 2 * z

with FixtureScope() as scope:
    print(scope.get_fixture_value("theta"))

Recursive fixture evaluation detected automatically and RecursiveFixtureEvaluation exception is raised:

from pyfixture import fixture, FixtureScope

@fixture
def one(two):
    pass

@fixture
def two(three):
    pass

@fixture
def three(one):
    pass

with FixtureScope() as s:
    s.get_fixture_value("one")

Reallistic Example

from pyfixture import fixture, FixtureScope

@fixture
def existing_user():
    user = User.objects.get_or_create(username="myuser")
    yield user
    user.delete()

@fixture(name="given_existing_order")
def existing_order(existing_user):
    order = Order.objects.get_or_create(id=1, user=existing_user)
    yield order
    order.delete()

scope = FixtureScope()
order = scope.get_fixture_value("existing_order")
user = scope.get_fixture_value("user")
assert order.user is user
# ...

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

pyfixture-0.7.tar.gz (18.4 kB view hashes)

Uploaded Source

Built Distribution

pyfixture-0.7-py2.py3-none-any.whl (20.0 kB view hashes)

Uploaded Python 2 Python 3

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page