An API Contract Test Prompt That Turns an OpenAPI Spec Into Tests
A reusable API contract test prompt that reads an OpenAPI spec and returns runnable schema, status, and negative-path tests. Copy the prompt.
An OpenAPI spec is a promise. Every endpoint declares its parameters, its response schema, its status codes, its error shape. The trouble is nobody checks the promise until a client breaks in production because someone quietly changed a field from a string to an object.
An API contract test prompt closes that gap. You paste the spec, and it returns runnable tests that assert what the contract claims: the schema holds, required fields are required, the 400 comes back when you omit them, the 401 fires without auth. It reads the spec the way a strict client would and writes the tests you keep forgetting to.
The pages ranking for this today mostly explain what a platform does under the hood, then funnel you to a demo. Genuinely educational, but you leave without a prompt you can paste tomorrow. This post is the paste-able version, plus the model quirks that decide whether the generated tests actually run.
What a contract test asserts that a smoke test doesn't
A smoke test hits an endpoint and checks it returns 200. That's it. It'll happily pass while the response silently dropped a required field or changed a type.
Contract tests assert the shape. For a single POST /orders endpoint, the contract implied by the spec includes:
- Schema conformance. Every field in the 201 response matches the declared type and format.
- Required-field enforcement. Omit a required field, get a 400, not a 500 or a silent default.
- Status coverage. Each documented status (201, 400, 401, 409) has a test that triggers it.
- Header policy. Content-type, auth, and pagination headers behave as declared.
- Error contract. The error body matches the documented error schema, not an ad-hoc stack trace.
Total Shift Left's writeup on how AI generates API tests from OpenAPI lays out the same reasoning pipeline: parse the spec, reason about the cases it implies but doesn't enumerate, author the tests. What it doesn't hand you is the prompt. The reasoning is the easy part to describe and the hard part to reuse, which is exactly why a locked prompt matters.
Anatomy of the API contract test prompt
Role first, spec in a fenced block, framework and output contract last. On a long spec the trailing contract is what keeps the output runnable instead of a prose essay about testing:
Role: You generate API CONTRACT tests from an OpenAPI spec. You assert
the published shape: schema, status codes, required fields, error bodies.
OpenAPI spec:
"""
{{openapi_spec}}
"""
Target framework: {{test_framework}}
Base URL variable: {{base_url}}
Auth: {{auth_scheme}}
For every path + method, generate:
1. Happy path: valid request, assert status + full schema.
2. One negative test per documented error status.
3. Required-field omission tests (expect the documented 4xx).
4. Type/format boundary tests where the spec constrains a field.
Output contract (return runnable code only, no prose):
- One test file, grouped by endpoint with a comment header per group.
- Assertions reference field names from the spec, not guesses.
- If the spec omits an error schema, add a plain comment: "spec: no error schema".
- Do not invent endpoints or fields absent from the spec.
{{openapi_spec}} is the artifact you already have. {{test_framework}} pins the output to your stack (pytest, Jest with supertest, Go's httptest) so you don't get a random one. Set them and the report is runnable, not aspirational.
The "don't invent" line earns its place
LLMs pattern-complete. Give a model an incomplete spec and it'll cheerfully add plausible endpoints and fields that don't exist, because a fuller API "looks right." That's how you get tests for routes your service never had. The explicit Do not invent endpoints or fields absent from the spec instruction is the single most important line in the prompt for trustworthiness. Keep it, and keep it near the output contract where the model weights it.
Model behavior for contract generation
The generated tests either run or they don't, and that comes down to how tightly the model holds the framework and the field names.
| Model | Spec parsing | Framework fidelity | Watch for |
|---|---|---|---|
| Claude (Sonnet/Opus) | Resolves $ref and nested schemas well | Sticks to the named framework closely | May over-generate boundary tests; cap per endpoint |
| GPT-4o / GPT-5 | Strong; fast on large specs | Good, but restate the framework on the last line | Occasionally invents a field on a thin spec, so keep the "don't invent" line |
| Cursor / Claude Code | Reads adjacent code, matches your existing test style | Best when your repo already has a test to mirror | Wants to run and fix tests; great as a second pass, not the first |
The honest recommendation: generate the suite with Claude or GPT from the spec alone, then open it in Cursor or Claude Code to align it with your repo's fixtures and run it. Generating from the spec keeps the tests tied to the contract; the agent pass ties them to your codebase. Two passes, two tools, each doing what it's good at.
Speakeasy's contract testing with OpenAPI writeup is worth reading for why the spec should be the source of truth in the first place, but note it's a workflow overview, not a prompt. That's the recurring shape of this whole SERP: strong on the "why," empty on the copyable "how."
Variables you'll set
| Variable | Required | What it is |
|---|---|---|
{{openapi_spec}} | Yes | The OpenAPI/Swagger document, YAML or JSON, pasted verbatim |
{{test_framework}} | Yes | The exact framework, e.g. "pytest + httpx" or "Jest + supertest" |
{{base_url}} | No | The base URL or the env var name your tests should read |
{{auth_scheme}} | No | How the endpoint authenticates, e.g. "JWT in Authorization header" |
Scope each run to one spec, or one tag within a large spec. A 300-endpoint spec in one shot produces shallow tests for all of them; a tag at a time produces deep tests for each.
Getting started
- Export or copy the OpenAPI spec for the service you're testing.
- Paste it into
{{openapi_spec}}and set{{test_framework}}to your stack. - Name
{{auth_scheme}}so the auth tests come out right. - Run on Claude or GPT and skim for invented fields (there shouldn't be any).
- Drop the file into your repo and open it in Cursor to wire fixtures.
- Run the suite; fix the handful that need real request bodies.
- Re-run the prompt per tag as the spec grows.
For the full loop, the API Contract Test Harness packages this generator with a spec-diff prompt that flags which contract tests to re-run when the spec changes, so a schema edit doesn't quietly break clients.
The API Contract Test Harness does this end-to-end: an {{openapi_spec}} variable feeds a locked, framework-pinned test file, and a bundled diff prompt tells you which contract tests to re-run after a spec change. It's part of The Complete AI Prompts Bundle, a one-time lifetime license to the whole catalog plus every pack added later, sensible if you test more than one API.
Watch one failure mode: a spec that's out of date generates tests for the API you documented, not the one you shipped. Contract tests are only as honest as the spec. If they all pass but clients break, the spec drifted, not the code.
Contract tests slot next to two neighboring jobs. When a whole endpoint contract is about to change, the detect breaking API changes prompt tells you whether it's a major bump before you ship it. And for the endpoints that talk to each other, the integration test generation prompt covers the wiring these contract tests deliberately don't. The rest of the engineering set lives in the catalog.
Browse the prompt catalog →Common questions
What is an API contract test prompt?
How is contract testing different from integration testing?
Can I just paste my spec into ChatGPT and ask for tests?
Get the prompt packs this guide is built on
Ready-to-paste prompts with documented variables and usage guides for ChatGPT, Claude, and Gemini. One-time payment, own it forever.
More prompt guides

A Test Coverage Gap Prompt That Finds the Code Your Tests Skip
Coverage reports lie by omission. A file reads 92% line coverage, the dashboard turns green, and everyone moves on. Then a null value slips through an error branch nobody asserted, and the incident ch…

A STRIDE Threat Modeling Prompt That Skips the Workshop
Threat modeling has a scheduling problem. It's the security practice everyone agrees matters and almost nobody does, because the honest version means booking a room, three engineers, and a security le…

AI Agent Fleet Operations: A Playbook Prompt for Running Many Agents
Running one AI agent is a demo. Running twenty of them, each with its own job, its own model, and its own way of failing, is an operations problem nobody warned you about. Suddenly you need to know wh…