pytest-bdd
Pytest-bdd is a pytest plugin that implements a subset of the Gherkin language to enable automating project requirements testing and facilitate Behavior-Driven Development (BDD). It integrates seamlessly with pytest, allowing reuse of fixtures and plugins, unifying unit and functional tests, and simplifying continuous integration server configuration. The library is actively maintained, with version 8.1.0 currently available, and often releases updates to ensure compatibility with the latest Gherkin specification.
Warnings
- breaking Step arguments are no longer fixtures since version 6.0.0 and 8.0.0. In previous versions, parsed step arguments automatically became pytest fixtures. This behavior was removed to align with official Gherkin specifications and avoid conflicts with actual fixtures.
- breaking Feature-level and vertical example tables are no longer supported since version 6.0.0 and 8.0.0. Pytest-bdd now strictly adheres to Gherkin's specification, which only supports example tables within `Scenario Outline` sections.
- breaking The behavior of parsing variable templates (`<variable>`) in steps changed significantly in versions 6.0.0 and 8.0.0. Previously, these were parsed in both `Scenario` and `Scenario Outline`. Now, they are only parsed for `Scenario Outline` steps.
- gotcha By default, `pytest-bdd` uses the current module's path to find feature files. This can lead to issues if feature files are organized in a different directory structure.
- gotcha When using tags in `.feature` files, if `pytest` is run with the `--strict-markers` option, these tags must also be explicitly declared in the `markers` setting of your `pytest.ini` file. Tag names should also be Python-compatible variable names.
- breaking Since version 8.0.0, `pytest-bdd` uses the official Gherkin parser. This introduced several strictness changes: multiline steps must use triple-quotes, all feature files must start with `Feature:`, and tags can no longer contain spaces.
Install
-
pip install pytest-bdd
Imports
- scenario
from pytest_bdd import scenario
- given
from pytest_bdd import given
- when
from pytest_bdd import when
- then
from pytest_bdd import then
- parsers
from pytest_bdd import parsers
Quickstart
import pytest
from pytest_bdd import scenario, given, when, then
# --- content of features/example.feature ---
# Feature: Basic feature
# Scenario: Run a simple scenario
# Given I have a value of 10
# When I add 5 to it
# Then the value should be 15
# --- content of tests/test_example.py ---
@scenario('../features/example.feature', 'Run a simple scenario')
def test_simple_scenario():
pass
@pytest.fixture
def initial_value():
return {}
@given('I have a value of 10')
def i_have_value_10(initial_value):
initial_value['value'] = 10
@when('I add 5 to it')
def i_add_5(initial_value):
initial_value['value'] += 5
@then('the value should be 15')
def the_value_should_be_15(initial_value):
assert initial_value['value'] == 15
# To run this example:
# 1. Create a directory structure: project_root/features/ and project_root/tests/
# 2. Save the .feature content into features/example.feature
# 3. Save the Python code into tests/test_example.py
# 4. Run `pytest` from `project_root`