Tavern ist ein cleveres Stück Ingenieurskunst. Es lässt sich in pytest integrieren, ermöglicht es Ihnen, einen API-Test als YAML-Datei zu beschreiben und diese Datei wie einen normalen pytest-Test auszuführen. Sie erhalten das gesamte Ökosystem von pytest kostenlos: Fixtures, Plugins, parallele Ausführungen mit pytest-xdist, Code-Coverage, denselben Befehl, den Ihr Python-Team bereits verwendet. Für ein Backend-Team, das in pytest arbeitet, fühlt sich das Schreiben einer weiteren test_*.tavern.yaml neben den Unit-Tests natürlich an.
Die Reibung entsteht, sobald die YAML-Datei wächst. Eine einzelne Anfrage, die einen Body sendet, einen Token speichert und einige Antwortfelder überprüft, verwandelt sich in einen verschachtelten Block von request-, response-, save- und verify_response_with-Schlüsseln, die Sie exakt richtig einrücken müssen. Mehrstufige Abläufe (Anmelden, Ressource erstellen, zurücklesen, löschen) stapeln diese Blöcke zu einer langen Datei, bei der ein falsch platziertes Leerzeichen die Analyse unterbricht und der vom Test überprüfte API-Vertrag ganz woanders liegt: in einer Swagger-Datei, einer Wiki-Seite oder einer Postman-Sammlung, die vor Monaten veraltet ist.
Was Tavern gut macht
Beginnen wir mit dem Lob, denn Tavern verdient es.
Es setzt auf pytest auf, anstatt es zu ersetzen. Tavern ist ein pytest-Plugin. Sie installieren es mit pip install tavern, legen eine YAML-Datei in Ihrem Testverzeichnis ab, und pytest entdeckt und führt sie wie jeden anderen Test aus. Das bedeutet, Sie behalten jede pytest-Gewohnheit bei, die Ihr Team bereits hat: -k zum Filtern, -x zum Stoppen beim ersten Fehler, pytest-html für Berichte, pytest-xdist für parallele Ausführungen, Fixtures für die gemeinsame Einrichtung. Nichts an Ihrem Runner ändert sich. Für einen Python-Shop ist das ein echter Vorteil, und nur wenige API-Testwerkzeuge lassen sich so sauber in eine bestehende Suite integrieren.
Die YAML ist deklarativ und lesbar. Ein einfacher Tavern-Test ist wirklich leicht zu überblicken:
test_name: Get a single order
stages:
- name: Fetch order 1042
request:
url: https://api.shop.test/orders/1042
method: GET
response:
status_code: 200
json:
id: 1042
status: shipped
Kein Klebecode, keine Assertions-Bibliothek zum Importieren, keine Testharness zum Schreiben. Die Anfrage und die erwartete Antwort stehen nebeneinander. Für die Überprüfung eines Statuscodes und ein paar Feldern liest sich das besser als das entsprechende requests plus assert in Python.
Variablen speichern und verketten. Tavern kann einen Wert aus einer Antwort extrahieren und mit save und {variable}-Substitution in die nächste Phase injizieren, sodass ein Anmelde- und dann Aufruf-Ablauf ohne benutzerdefinierten Code funktioniert:
stages:
- name: Log in
request:
url: https://api.shop.test/auth/login
method: POST
json:
username: tester
password: hunter2
response:
status_code: 200
save:
json:
token: access_token
- name: Read the profile with the saved token
request:
url: https://api.shop.test/me
method: GET
headers:
Authorization: "Bearer {token}"
response:
status_code: 200
Es kann mehr als HTTP. Tavern testet auch MQTT, was wichtig ist, wenn Sie mit IoT oder nachrichtengetriebenen Systemen arbeiten. Und da pytest darunter liegt, können Sie YAML-API-Tests und reguläre Python-Tests im selben Durchlauf und im selben Bericht mischen.
Nichts davon ist Marketing. Tavern ist ein solides Werkzeug. Die Frage ist, ob seine Annahmen mit Ihren übereinstimmen.
Wo sich der YAML-Boilerplate-Code ansammelt
Drei Nachteile sind mit dem Tavern-Modell verbunden, und ob sie ins Gewicht fallen, hängt davon ab, wie groß Ihre Suite wird.
YAML ist abstandsrelevant, und das Schema ist tief. Das einfache Beispiel oben ist sauber. Ein realistischer Test ist es nicht. Sobald Sie Header, Abfrageparameter, einen Request-Body, Response-Body-Assertions, Typenprüfungen, gespeicherte Variablen und externe Funktionen verify_response_with hinzufügen, verschachteln Sie vier und fünf Ebenen tief in einem Format, bei dem ein falsch platziertes Leerzeichen ein Parse-Fehler ist, keine klare Meldung. Editoren vervollständigen Taverns Schlüssel nicht so, wie eine IDE eine Python-Methode automatisch vervollständigt, daher prüfen Sie die Dokumentation, ob es status_code oder status, json oder body ist, bei jedem neuen Feld.
Der Test und der API-Vertrag sind zwei separate Artefakte. Ihre Tavern-YAML-Datei enthält die URL, die Methode, die erwarteten Felder und deren Typen fest codiert. Die eigentliche API-Definition befindet sich in einer OpenAPI-Datei, in den Routen-Decorators eines Frameworks oder niemand ist sich ganz sicher, wo. Wenn die API einen Feldnamen ändert, teilt nichts dies der YAML-Datei mit. Der Test beharrt weiterhin auf der alten Form, bis er in CI fehlschlägt oder, schlimmer noch, weiterhin mit einer veralteten Erwartung bestanden wird. Jemand muss die beiden manuell synchron halten, und dieser Jemand ist normalerweise derjenige, bei dem der Fehler um 2 Uhr morgens landet.
Es setzt eine Python-Toolchain und Python-Entwickler voraus. Tavern ist großartig, wenn Ihre Tester Python schreiben. Wenn Ihre QA-Gruppe, Ihre Frontend-Ingenieure oder Ihre Produktmanager einen Test hinzufügen oder lesen möchten, stoßen sie gleichzeitig auf pip, virtualenvs, pytest-Konventionen und YAML-Schema-Regeln, nur um eine HTTP-Anfrage zu senden und eine Antwort zu überprüfen. Der Einstieg ist für jeden außerhalb der Python-Welt steil.
Der "ohne YAML"-Weg
Die Alternative besteht darin, Tests nicht mehr als Textdateien zu erstellen, sondern sie anhand der bereits vorhandenen API-Definition zu erstellen.
In Apidog sind die API-Spezifikation, die Anfrage und der Test dasselbe Objekt. Sie importieren oder entwerfen Ihre API einmal (OpenAPI, Swagger oder eine Postman-Sammlung lassen sich mit einem Klick importieren), und jeder Endpunkt trägt sein echtes Schema mit sich. Sie erstellen ein Testszenario, indem Sie diese Endpunkte visuell verketten: Ziehen Sie den Anmeldeaufruf herein, ziehen Sie den Aufruf herein, der den Token benötigt, und leiten Sie den Wert weiter, ohne save:-Blöcke oder {variable}-Zeichenfolgen von Hand zu schreiben. Assertions sind Kontrollkästchen und Ausdrücke in einem Panel, keine eingerückten YAML-Schlüssel, die Sie sich merken müssen.
Da der Test auf Basis der Spezifikation erstellt wird, ist die Spezifikation die einzige Quelle der Wahrheit. Ändern Sie ein Antwortfeld im Design, und die Testszenarien, die darauf verweisen, zeigen die Änderung an, anstatt stillschweigend abzuweichen. Das ist der Teil, den Tavern strukturell nicht leisten kann: Seine YAML-Datei hat keine Verbindung zum Vertrag.
Und wenn es Zeit ist zu automatisieren, verlieren Sie nicht die Headless-, CI-freundliche Eigenschaft, die Tavern attraktiv machte. Die Apidog CLI führt dieselben Szenarien von der Kommandozeile aus, in CI, ohne GUI, genau so aus, wie pytest heute Ihre Tavern-Dateien ausführt.
Die Apidog CLI installieren und ausführen
Der Runner ist ein kostenloses npm-Paket namens apidog-cli. Installieren Sie es global:
npm install -g apidog-cli
Führen Sie dann ein Testszenario mit dem Befehl apidog run aus:
apidog run --access-token $APIDOG_ACCESS_TOKEN -t 605067 -e 1629989 -r cli
Hier ist, was jedes Element bewirkt:
--access-tokenauthentifiziert den Durchlauf gegenüber Ihrem Apidog-Konto. Generieren Sie den Token im CI/CD-Tab des Szenarios und speichern Sie ihn als Geheimnis, niemals in der Datei.-tist die ID des Testszenarios.-eist die Umgebungs-ID (Entwicklung, Staging, Produktion), sodass dasselbe Szenario die richtige Basis-URL und die richtigen Variablen verwendet.-rwählt die Reporter aus.cligibt eine lesbare Ausgabe im Terminal aus.
Sie müssen sich diese IDs nicht merken. Öffnen Sie das Testszenario in Apidog, wechseln Sie zum CI/CD-Tab, wählen Sie die Kommandozeilenoption und klicken Sie auf "Token generieren". Apidog erstellt den vollständigen Befehl apidog run für Sie, wobei die Szenario-ID und die Umgebungs-ID bereits ausgefüllt sind. Kopieren Sie ihn und verschieben Sie den Token dann in ein CI-Geheimnis.
Wenn Sie es lieber nicht global installieren möchten, insbesondere auf einem temporären CI-Runner, führen Sie es mit npx aus:
npx apidog-cli run --access-token $APIDOG_ACCESS_TOKEN -t 605067 -e 1629989 -r cli
Die Reporter umfassen cli, html, json und junit. Für CI ist die nützliche Kombination -r html,junit: junit gibt das Standard-XML aus, das fast jedes CI-Dashboard in einen Pass/Fail-Baum parst, und html erzeugt einen durchsuchbaren Bericht, den Sie als Build-Artefakt archivieren können. Fügen Sie --out-dir hinzu, um zu steuern, wo sie landen:
apidog run --access-token $APIDOG_ACCESS_TOKEN -t 605067 -e 1629989 -r html,junit --out-dir ./apidog-reports
Für die vollständige Flag-Liste Ihrer installierten Version führen Sie apidog run --help aus.
Gegenüberstellung
| Tavern | Apidog | |
|---|---|---|
| Testformat | YAML-Dateien (*.tavern.yaml) |
Visuelle Szenarien, die auf der Spezifikation basieren |
| Laufzeit | Python + pytest | Headless apidog run (npm-Paket) |
| Erstellung | Manuelles Schreiben und Einrücken von YAML | Endpunkte per Drag & Drop verketten, Assertions über Kontrollkästchen |
| API-Vertrag | Separates Artefakt, manuell synchron gehalten | Spezifikation ist die Quelle der Wahrheit für den Test |
| Variablenverknüpfung | save:-Blöcke und {var}-Substitution |
Werte zwischen Schritten in der Benutzeroberfläche übergeben |
| Reporter | pytest-html, JUnit über pytest-Plugins |
cli, html, json, junit integriert |
| Wer Tests schreiben kann | Python-vertraute Tester | Jeder im Team, einschließlich Nicht-Programmierer |
| Protokolle | HTTP und MQTT | HTTP, plus SOAP, WebSocket, gRPC und mehr |
Tavern punktet, wenn Ihr Team voll auf Python setzt und Sie möchten, dass Tests im selben Repository und im selben pytest-Durchlauf wie Ihre Unit-Tests liegen. Apidog punktet, wenn Sie die YAML-Wartung aufgeben, den Vertrag und den Test als eine Einheit betrachten und Personen, die kein Python schreiben, Tests beitragen lassen möchten.
Integration in CI
Der Headless-Lauf ist der entscheidende Punkt beim Übergang von einer lokalen Testdatei zu einer Pipeline. Hier ist die Struktur für GitHub Actions:
name: API tests
on: [push, pull_request]
jobs:
api-tests:
runs-on: ubuntu-latest
steps:
- name: Install Apidog CLI
run: npm install -g apidog-cli
- name: Run API test scenario
run: |
apidog run \
--access-token "$APIDOG_ACCESS_TOKEN" \
-t 605067 \
-e 1629989 \
-r html,junit \
--out-dir apidog-reports
env:
APIDOG_ACCESS_TOKEN: ${{ secrets.APIDOG_ACCESS_TOKEN }}
- name: Upload report
if: always()
uses: actions/upload-artifact@v4
with:
name: apidog-report
path: apidog-reports
Der Token stammt aus Repository-Geheimnissen und erreicht den Schritt als Umgebungsvariable. Das if: always() im Upload-Schritt bedeutet, dass Sie den Bericht auch dann erhalten, wenn die Tests fehlschlagen, was genau der Zeitpunkt ist, an dem Sie ihn lesen möchten. Wenn eine Assertion fehlschlägt, beendet der apidog run-Schritt mit einem Nicht-Null-Exit-Code, der Job wird rot angezeigt und der Pull-Request zeigt eine fehlgeschlagene Überprüfung an.
Dieses Exit-Code-Verhalten ist das Qualitätsgate, und es funktioniert auf dieselbe Weise wie bei Tavern: CI liest den Exit-Code jedes Schritts, ein Nicht-Null-Exit lässt den Job fehlschlagen, und ein fehlgeschlagener Job blockiert das Mergen oder das Deployment. Sie müssen nichts Zusätzliches konfigurieren. Für tiefere Pipeline-Setups decken Apidog CLI in Ihrer CI/CD-Pipeline und die GitHub Actions-Anleitung auch GitLab CI- und Jenkins-Varianten ab.
Ein Hinweis zu pytest und der weiteren Python-Testwelt
Das Verlassen von Taverns YAML bedeutet nicht, pytest aufzugeben. Viele Teams behalten ihre reinen Python-Unit- und Integrationstests in pytest und verwenden Apidog für die API-Vertragsschicht, den Teil, in dem der Test die Spezifikation verfolgen und auch für Nicht-Python-Beitragende ausgeführt werden sollte. Die beiden schließen sich nicht gegenseitig aus. Taverns Wert bestand immer darin, pytest-Nutzern zu ermöglichen, API-Tests in einem leichteren Format als rohen requests-Code zu schreiben; Apidogs Wert liegt darin, diese API-Tests den Vertrag verfolgen zu lassen und lesbar zu bleiben, wenn die Suite über eine Handvoll Dateien hinauswächst.
Wenn Sie auch andere Runner in Betracht ziehen, gilt dieselbe Logik für Postmans Kommandozeilen-Ansatz in Postman CLI vs Newman und für das Ausführen von Sammlungen ohne zusätzliche Tools in API-Tests ohne Postman.
FAQ
Ist die Apidog CLI kostenlos? Ja. Das npm-Paket apidog-cli kann kostenlos installiert und mit npm install -g apidog-cli ausgeführt werden. Es führt die Testszenarien aus Ihrem Apidog-Projekt aus, sodass das, was Sie ausführen können, von Ihrem Apidog-Plan abhängt, aber der Kommandozeilen-Runner selbst ist kein separates kostenpflichtiges Produkt.
Kann ich pytest weiterhin zusammen mit Apidog verwenden? Ja. Behalten Sie Ihre Python-Unit- und Integrationstests in pytest und verwenden Sie Apidog für die API-Vertragstestschicht. Viele Teams nutzen beides. Der Unterschied ist, dass Apidog-Tests die Spezifikation verfolgen, anstatt sie in einer separaten Datei fest zu codieren.
Wie blockiert Apidog einen fehlerhaften Merge in CI? Über den Exit-Code. Wenn eine Assertion fehlschlägt, beendet apidog run mit einem Nicht-Null-Exit-Code. CI liest diesen Exit-Code, markiert den Schritt als fehlgeschlagen und blockiert den Merge oder das Deployment. Sie müssen nichts Zusätzliches konfigurieren, damit dies funktioniert.
Welchen Reporter sollte ich für CI verwenden? Verwenden Sie junit für das maschinenlesbare Ergebnis, das Ihr CI-Dashboard in einen Pass/Fail-Baum parst, und fügen Sie html hinzu, wenn Sie einen durchsuchbaren Bericht als Artefakt speichern möchten. Eine gängige Wahl ist -r html,junit, wobei cli für eine lesbare Build-Log-Ausgabe aktiviert bleibt.
Testet Apidog nur HTTP, wie Taverns HTTP-Modus? Nein. Apidog deckt HTTP plus SOAP, WebSocket, Server-Sent Events und gRPC ab. Tavern fügt MQTT zu HTTP hinzu, was der einzige Bereich ist, in dem die Protokollabdeckung über Apidog hinausgeht. Beachten Sie dies, wenn MQTT für Ihren Stack zentral ist.
Die ehrliche Erkenntnis
Tavern ist eine saubere Methode, um API-Tests zu schreiben, wenn Sie bereits in pytest und YAML denken, und die pytest-Integration ist wirklich das beste Merkmal. Der Nachteil ist die YAML selbst: Sie wird tief und brüchig, wenn Suiten wachsen, und sie hat keine Verbindung zum API-Vertrag, den sie verifiziert. Wenn Sie dasselbe Headless-Verhalten, das laut in CI fehlschlägt, ohne manuelles Einrücken von YAML und ohne eine zweite Kopie Ihrer Spezifikation zu pflegen, wünschen, ist das Erstellen von Tests gegen den Vertrag und deren Ausführung mit apidog run der leichtere Weg.
Laden Sie Apidog herunter und importieren Sie eine bestehende API, um den "Spezifikation ist der Test"-Workflow kennenzulernen, bevor Sie sich festlegen. Der Einstieg ist kostenlos.
