Skip to content

HATEOAS as a REST Constraint — The Sixth Pillar of RESTful Design

DodaTech Updated 2026-06-28 2 min read

In this tutorial, you will learn about HATEOAS as a REST Constraint. We cover key concepts, practical examples, and best practices to help you master this topic.

HATEOAS is part of REST's uniform interface constraint, requiring that resources include hypermedia links that describe available transitions and guide client interactions dynamically.

What You'll Learn

  • How HATEOAS fits into REST's six constraints
  • The difference between HATEOAS and non-HATEOAS APIs
  • Why HATEOAS completes the REST architecture

Why It Matters

Without HATEOAS, your API is just HTTP CRUD. HATEOAS is what makes an API truly RESTful by enabling runtime discovery and reducing coupling.

flowchart TD
    A["REST Constraints"] --> B["Client-Server"]
    A --> C["Statelessness"]
    A --> D["Cacheability"]
    A --> E["Uniform Interface"]
    E --> F["Resource Identification\n(URIs)"]
    E --> G["Resource Manipulation\n(Representations)"]
    E --> H["Self-Descriptive\nMessages"]
    E --> I["HATEOAS\n(Hypermedia)"]
    style I fill:#dbeafe,stroke:#2563eb

Code Examples

# Non-HATEOAS approach (clients hardcode URLs)
ORDERS_URL = "https://api.example.com/orders"
ORDER_URL = "https://api.example.com/orders/{id}"
PAYMENTS_URL = "https://api.example.com/orders/{id}/payments"

# HATEOAS approach (server provides URLs)
order = requests.get(f"https://api.example.com/orders/123").json()
payment_url = order["_links"]["pay"]["href"]
# Client just follows the link
// Non-HATEOAS response
{
  "id": "ORD-123",
  "status": "pending",
  "total": 2999
}

// HATEOAS response
{
  "id": "ORD-123",
  "status": "pending",
  "total": 2999,
  "_links": {
    "self": { "href": "/orders/ORD-123", "method": "GET" },
    "pay": { "href": "/orders/ORD-123/payments", "method": "POST" },
    "cancel": { "href": "/orders/ORD-123", "method": "DELETE" }
  }
}

Common Mistakes

1. Claiming REST Compliance Without HATEOAS

Without HATEOAS, your API is HTTP-based but not fully RESTful.

Links should reflect current state. A shipped order shouldn't have "ship" link.

3. Using HATEOAS Only for Collection Endpoints

Every resource response should include relevant hypermedia links.

When order status changes, available actions change too.

Links should be specific to the resource context and available actions.

Practice Questions

  1. Which REST constraint includes HATEOAS?
  2. How does HATEOAS relate to the uniform interface?
  3. Why isn't every HTTP API a REST API?
  4. What happens if a client ignores HATEOAS links?
  5. Can you have REST without HATEOAS?

Answers:

  1. The uniform interface constraint.
  2. HATEOAS makes messages self-descriptive by including available actions.
  3. REST requires HATEOAS, self-descriptive messages, and other constraints that HTTP-only APIs often skip.
  4. The client still works but is tightly coupled to URL patterns.
  5. Technically not, but many practical APIs skip it.

Challenge: Take a simple REST API without HATEOAS and redesign it with hypermedia links. Show how each endpoint response changes.

FAQ

Is HATEOAS the most ignored REST constraint?

: Yes. Most APIs that call themselves RESTful omit HATEOAS for simplicity.

Does HATEOAS make APIs slower?

: Minimal impact. Links add a small amount of JSON to responses.

Can I add HATEOAS to an existing API?

: Yes, incrementally. Add _links to responses without breaking existing clients.

What's Next

Explore Links and Rels in detail, then learn about Link Formats including HAL and JSON:API.

Built by the developers of DodaTech

Doda Browser, DodaZIP & Durga Antivirus Pro