API Testing

API Testing Explained: Requests, Responses, and Assertions

Learn API testing through HTTP requests, responses, methods, status codes, headers, parameters, JSON, authentication, assertions, and a Playwright example.

Software Testing Automation Editorial TeamEditorial publishing identity
Published
Reading time
6 min read
Difficulty
Beginner
Audience
For Student, Manual tester, QA engineer, Developer
Two squares exchanging a request and a response along right-angled arrows
IllustrationTwo squares exchanging a request and a response along right-angled arrows.

Article overview

What you will learn

  • What APIs, clients, servers, requests, and responses mean
  • How HTTP methods, status codes, headers, and parameters work
  • Why status-code-only checks are incomplete
  • How to test a JSON API with Playwright request context
  • How to cover positive, negative, and authorization scenarios

Before you begin

Prerequisites

  • Basic command-line familiarity
  • Node.js installed for the practical example
  • A Playwright Test project for the practical example

API testing in plain words

Think of a restaurant. The menu and the waiter are the interface: you do not walk into the kitchen, you make a request in an agreed format and get back a predictable result. An API is that waiter — one piece of software asking another for something, in a format both sides agreed on in advance.

Testing the website means checking the dining room: does the menu look right, does the table wobble. Testing the API means checking the waiter: if I ask for something that does not exist, do I get a polite refusal or a shrug? If I ask for someone else's order, do I get it? Those questions are faster and more precise to ask directly, without going through the screen at all.

The words you will hear, in simple terms.
TermWhat it meansEveryday comparison
RequestOne system asking another to do somethingPlacing an order
ResponseWhat comes backThe food, or an apology
EndpointThe specific address you send the request toThe counter you queue at
Status codeA short number saying how it went"Ready", "Not on the menu", "Kitchen on fire"
Payload / bodyThe data being sent or returnedWhat is actually on the plate
TokenProof of who you areYour membership card

API and HTTP basics

In a common web API, a client sends an HTTP request and a server returns an HTTP response. The request describes the intended operation. The response reports an outcome and may include data.

Parts of an HTTP request

  • A method expresses intent. GET retrieves a representation, POST often creates or processes data, PUT replaces a resource, PATCH applies a partial change, and DELETE requests removal.
  • A path parameter identifies part of the resource path, such as /products/42.
  • A query parameter modifies a request, such as /products?category=books.
  • A header carries metadata such as accepted content type or authorization information.
  • A request body carries data, often JSON, for methods that submit or change information.

Parts of an HTTP response

A response contains a status code, headers, and optionally a body. Status codes are grouped into informational, successful, redirection, client-error, and server-error classes. A 200 response says the request completed successfully at the HTTP level; it does not prove that every returned field is correct.

Assertions beyond the status code

  • Check that required fields exist and have appropriate types.
  • Check important values and business rules, not only field presence.
  • Check response headers such as content type where relevant.
  • Check schema compatibility without making harmless optional additions impossible.
  • Check side effects by retrieving or observing the changed resource.
  • Check that unauthorized requests do not expose protected data.
  • Check useful error structure for invalid input.

Practical example with Playwright

tests/products-api.spec.ts TypeScript
import { test, expect } from '@playwright/test'; test('returns an available product', async ({ request }) => { const response = await request.get('/api/products/42'); expect(response.status()).toBe(200); expect(response.headers()['content-type']).toContain('application/json'); const product = await response.json(); expect(product).toMatchObject({ id: 42, available: true, }); expect(product.name).toEqual(expect.any(String)); expect(product.price).toBeGreaterThan(0);});

The test sends a GET request, verifies the status and content type, parses the JSON body, then checks identity, availability, name type, and a basic price rule. The project must configure baseURL or use a complete test-environment URL. In a real suite, create known data through a fixture and clean it up after the test.

Positive and negative scenarios

ScenarioExampleWhat to inspect
PositiveRequest an existing productStatus, headers, fields, rules
Invalid inputSubmit a negative quantityClient-error status and useful validation details
Missing resourceRequest an unknown IDNot-found behavior without unrelated data
UnauthorizedOmit or invalidate credentialsAccess denial and no protected content
ConflictCreate a duplicate unique valueConflict handling and unchanged stored data
Server failureSimulate a controlled dependency errorSafe error response and observability

Authentication and the security boundary

Store test credentials in environment variables or a CI secret store, not source code. Use accounts and environments you are authorized to test. API functional tests can check access control behavior, but a security assessment requires an agreed scope, appropriate methods, and specialist review.

Common mistakes

  • Checking only a successful status code
  • Depending on shared data that another test can change
  • Logging tokens or personal data in failure output
  • Treating response order as meaningful when the contract does not guarantee it
  • Making schema checks so strict that compatible changes fail
  • Testing production or third-party systems without permission

Key takeaways

  • An API request expresses an operation; a response reports the outcome and data.
  • Status, headers, body, schema, business rules, and side effects can all matter.
  • Positive and negative scenarios provide complementary evidence.
  • Control test data and protect credentials.
  • A 2xx status alone does not prove response correctness.

Your first week

  1. Ask for the API documentation. If none exists, that is your first finding.
  2. Send one GET request to a read-only endpoint using any API client and read the whole response.
  3. Write down what each field should contain, and check whether it does.
  4. Try three things that should fail: an ID that does not exist, an invalid value, and no credentials at all.
  5. Note whether the errors are clear and whether anything leaks that should not.
  6. Turn the two most valuable checks into automated tests.
  7. Add them to your pipeline so they run on every change.

Frequently asked questions

Do I need to know programming to test APIs?

Not to start. A graphical API client lets you send requests and inspect responses without writing any code. Programming becomes necessary when you want those checks to run automatically on every change.

If the API is tested, do we still need browser tests?

Yes, but fewer of them. API tests confirm the services behave; browser tests confirm a person can actually complete the journey. Keep a small set of browser tests for the critical paths and push the detailed rule-checking down to the API.

Why is checking the status code not enough?

A 200 only means the request was handled. The response can still contain the wrong price, a missing field, another customer's data, or an empty list where there should be results.

Can I test an API I do not own?

Only with permission. Sending unusual or high-volume requests to someone else's service without authorisation can breach their terms and can look like an attack. Use a sandbox environment where the provider offers one.

References and further reading

Was this article helpful?