Simple testing of RESTful APIs
npx @tessl/cli install tessl/pypi-tavern@2.17.0A comprehensive API testing framework that serves as a pytest plugin, command-line tool, and Python library for automated testing of RESTful APIs and MQTT-based systems. Tavern features a YAML-based test syntax that is both simple and highly customizable, allowing developers to write clear, maintainable API tests with minimal boilerplate.
pip install taverntavern-ciimport tavernFor programmatic test execution:
from tavern.core import runFor validation helpers:
from tavern.helpers import (
validate_jwt,
validate_regex,
validate_content,
check_jmespath_match
)For custom test implementations:
from tavern.request import BaseRequest
from tavern.response import BaseResponse# Run a single test file
tavern-ci test_api.tavern.yaml
# Run with logging
tavern-ci --stdout --debug test_api.tavern.yaml
# Run with global configuration
tavern-ci --tavern-global-cfg config.yaml test_api.tavern.yamlfrom tavern.core import run
# Run tests programmatically
exit_code = run(
in_file="test_api.tavern.yaml",
tavern_global_cfg="config.yaml",
tavern_strict=True
)
# Check if all tests passed
if exit_code == 0:
print("All tests passed!")
else:
print("Some tests failed!")# test_api.tavern.yaml
test_name: Test user creation API
stages:
- name: Create new user
request:
url: https://api.example.com/users
method: POST
json:
name: "John Doe"
email: "john@example.com"
response:
status_code: 201
json:
id: !anyint
name: "John Doe"
email: "john@example.com"
save:
json:
user_id: id
- name: Get created user
request:
url: https://api.example.com/users/{user_id}
method: GET
response:
status_code: 200
json:
id: "{user_id}"
name: "John Doe"Tavern uses a plugin-based architecture that supports multiple protocols and testing patterns:
The framework is designed for maximum developer productivity in API testing workflows, offering both declarative YAML-based testing and programmatic Python API access.
Primary interface for running Tavern tests programmatically or via command line. Supports global configuration, backend selection, and pytest integration.
def run(
in_file: str,
tavern_global_cfg: Union[dict, str, None] = None,
tavern_mqtt_backend: Union[str, None] = None,
tavern_http_backend: Union[str, None] = None,
tavern_grpc_backend: Union[str, None] = None,
tavern_strict: Union[bool, None] = None,
pytest_args: Union[list, None] = None,
) -> Union[ExitCode, int]Comprehensive validation functions for API responses including JWT validation, regex matching, schema validation, and content assertions using JMESPath.
def validate_jwt(response: requests.Response, jwt_key: str, **kwargs) -> Mapping[str, Box]
def validate_regex(
response: requests.Response,
expression: str,
*,
header: Optional[str] = None,
in_jmespath: Optional[str] = None,
) -> dict[str, Box]
def validate_content(response: requests.Response, comparisons: Iterable[dict]) -> None
def check_jmespath_match(parsed_response, query: str, expected: Optional[str] = None)Deep integration with pytest providing custom hooks, CLI options, automatic test file discovery, and seamless integration with pytest plugins and reporting.
def pytest_addhooks(pluginmanager)
def pytest_addoption(parser)
def pytest_collect_file(parent, path)
def add_parser_options(parser_addoption, with_defaults=True)Extensible plugin system supporting HTTP/REST, MQTT, and gRPC protocols with standardized interfaces for requests, responses, and session management.
class BaseRequest:
def __init__(self, session: Any, rspec: dict, test_block_config: TestConfig) -> None
@property
def request_vars(self) -> box.Box
def run(self)
class BaseResponse:
name: str
expected: Any
test_block_config: TestConfig
response: Optional[Any] = None
def verify(self, response)Comprehensive exception hierarchy for detailed error reporting and debugging, covering schema validation, key mismatches, protocol errors, and configuration issues.
class TavernException(Exception):
stage: Optional[dict]
test_block_config: Optional["TestConfig"]
is_final: bool = False
class BadSchemaError(TavernException)
class TestFailError(TavernException)
class KeyMismatchError(TavernException)class TavernArgParser(ArgumentParser):
def __init__(self) -> None
def main() -> NoneCLI Options:
--tavern-global-cfg: Path to global configuration file--tavern-http-backend: HTTP backend selection (default: "requests")--tavern-mqtt-backend: MQTT backend selection (default: "paho-mqtt")--tavern-grpc-backend: gRPC backend selection (default: "grpc")--tavern-strict: Response matching strictness level--tavern-file-path-regex: Test file pattern (default: *.tavern.ya?ml)--log-to-file: Log output to a file (defaults to tavern.log if no filename provided)--stdout: Log output to stdout--debug: Enable debug logging (only relevant with --stdout or --log-to-file)from typing import Union, Optional, Any, Mapping, Iterable
from _pytest.config import ExitCode
from box.box import Box
import requests
TestConfig = "tavern._core.pytest.config.TestConfig"