Reference guide · http-status · Published 2026-08-16 · 3 min read

HTTP 428 Precondition Required explained

HTTP 428 Precondition Required tells a client its request must include a precondition header to prevent a race. Learn when servers use 428 and how clients should respond.

Flat editorial illustration showing a lantern-style status readout with a neat row of stacked directory rails, each rail marked with an abstract tally.
Illustration: this article at a glance.

What 428 means

HTTP 428 Precondition Required is returned by a server when it wants a request to be made conditional, but the client did not include the required precondition. The server is saying: your request would have succeeded, but I refuse to apply it blindly because that could overwrite a newer version of the resource. Include a precondition header, such as If-Match or If-None-Match, and retry.

Editorial close-up illustration showing a lantern-style status readout with a neat row of stacked directory rails, each rail marked with an abstract tally.
Illustration: a closer look at the technique described above.

The status is a message about the request, not the resource's current state. It does not mean the resource is missing or the operation is impossible. It means the server policy demands that the client prove it is working from an up-to-date version.

Lost update problem

The reason a server requests a precondition is to prevent the lost update race. Consider two clients both about to edit the same record:

  1. Client A reads the resource at version 1.
  2. Client B reads the resource at version 1.
  3. Client A writes its changes; the resource becomes version 2.
  4. Client B writes its changes, silently overwriting A's work.

Without a precondition, B clobbers A and no one is told. If the server requires every write to carry If-Match: <etag-or-version>, then B's write sends a stale tag, the server returns 412 (or 428 first, telling B it must have sent a condition at all), and the conflict is surfaced to a human instead of overwritten silently.

This optimistic concurrency pattern is common in content management, collaborative documents, and APIs that store a mutable version.

Choosing preconditions

The two dominant preconditions are:

The status pair to understand together:

The flow a robust client should follow:

  1. Read the resource and capture its current entity tag.
  2. Send the mutation with If-Match: <etag>.
  3. If 412 comes back, re-read, surface the newer state, and ask the user how to resolve the conflict.
  4. If 428 comes back, treat it as "this endpoint demands a conditional request", retry with the precondition, and fix the client so it always sends one.

428 is a niche status. Practical sites rarely see it because most servers omit the requirement rather than enforce it, but it is the correct signal when you do enforce conditional writes. It belongs to the client error family, sits beside HTTP 412, and is the natural partner of HTTP 409 when a conflict must be reported instead of retried.

Need a website built, fixed, optimised, migrated or replaced?

This technical resource is written by CSMBAC, a small design and development studio. If you would rather hand the problem to a professional, the website service page explains how we build enquiry-ready websites.

Explore website services