Menu

API Design And Architecture

Learn API Design And Architecture for API Engineer for free: roadmap, examples, subskills, and a skill exam.

Published: January 21, 2026 | Updated: January 21, 2026

Why API Design and Architecture matters for API Engineers

Great APIs feel simple to use, scale predictably, and evolve without breaking clients. As an API Engineer, you turn business capabilities into dependable contracts: modeling resources, choosing versioning strategies, enforcing limits, supporting async workflows and webhooks, and shaping how gateways route, secure, and observe traffic.

Mastering this skill unlocks tasks like defining cross-team API standards, leading migration plans from v1 to v2, designing multi-tenant SaaS boundaries, and preventing outages due to breaking changes.

Who this is for

  • Backend engineers building or maintaining external/internal APIs
  • Platform engineers working with gateways, auth, and observability
  • Mobile/web/backend developers consuming APIs who want to design better ones

Prerequisites

  • Comfort with HTTP and JSON (status codes, headers, body)
  • Basic server development in any language
  • Familiarity with auth concepts (tokens, roles)

Learning path (practical roadmap)

  1. Milestone 1 — Resource modeling & naming

    Define clear nouns, plural resources, stable IDs, and relationships. Nail status codes and error formats.

    How to practice

    Model a simple Orders API: users, orders, order-items. Write endpoints and sample payloads.

  2. Milestone 2 — Versioning & backward compatibility

    Pick URL or header versioning; understand additive changes, deprecation, and migration windows.

    How to practice

    Publish v1, then introduce v2 with an additive field and new endpoint; keep v1 working.

  3. Milestone 3 — Extensibility & conventions

    Filtering, pagination, sorting, sparse fieldsets, consistent errors, and metadata envelopes.

    How to practice

    Add pagination and filter to Orders. Return standard error objects.

  4. Milestone 4 — Async flows & webhooks

    Design event types, delivery, retries, signature verification, and idempotent handlers.

    How to practice

    Emit order.created events with a retry policy. Implement webhook signature check.

  5. Milestone 5 — Rate limits & quotas

    Choose algorithms (token bucket/sliding window), return headers, and apply tenant-level quotas.

    How to practice

    Throttle write endpoints and expose X-RateLimit-* and Retry-After headers.

  6. Milestone 6 — API gateway concepts

    Routing, authentication, rate limiting, request/response transformation, and observability.

    How to practice

    Define routes for v1 vs v2, add auth, and inject correlation IDs for tracing.

  7. Milestone 7 — Multi-tenant design

    Isolate tenant data, choose header/path scoping, plan per-tenant limits and RBAC.

    How to practice

    Add tenant scoping to Orders (header X-Tenant-Id) and enforce row-level filters.

  8. Milestone 8 — Production readiness

    Contract tests, deprecation communication, error budgets, dashboards, and runbooks.

    How to practice

    Create a minimal change log and a deprecation plan for an endpoint.

Worked examples

1) Resource modeling: Orders, items, and relationships

Use plural nouns, predictable paths, and relationship sub-resources.

GET  /users/{user_id}/orders            # list a user's orders
POST /users/{user_id}/orders            # create
GET  /orders/{order_id}                 # retrieve
GET  /orders/{order_id}/items           # list items
POST /orders/{order_id}/items           # add item

Standard response shape with metadata and errors:

200 OK
{
  "data": [{ "id": "ord_123", "status": "pending", "total": 49.99 }],
  "meta": { "page": 1, "page_size": 20, "total": 57 }
}

Error example:

422 Unprocessable Entity
{
  "error": {
    "code": "validation_failed",
    "message": "quantity must be > 0",
    "details": [{ "field": "quantity", "issue": "min" }]
  }
}
2) Versioning: URL vs. header

URL versioning is explicit; header versioning keeps stable URLs and supports content negotiation.

# URL versioning
GET /v1/orders/{id}
GET /v2/orders/{id}

# Header versioning (media type)
GET /orders/{id}
Accept: application/vnd.orders.v2+json

Example server routes (Express):

// URL versioning
app.get('/v1/orders/:id', v1GetOrder)
app.get('/v2/orders/:id', v2GetOrder)

// Header versioning
app.get('/orders/:id', (req, res) => {
  const accept = req.get('Accept') || ''
  return accept.includes('vnd.orders.v2') ? v2GetOrder(req,res) : v1GetOrder(req,res)
})
3) Backward compatibility: additive change

Adding optional fields is safe; removing or renaming fields breaks clients.

# v1 response
{
  "id": "ord_123",
  "status": "pending"
}

# v2 adds an optional field (safe)
{
  "id": "ord_123",
  "status": "pending",
  "estimated_ship_at": "2026-02-01T10:00:00Z"
}

Communicate deprecations with headers:

Deprecation: true
Sunset: Wed, 01 Apr 2026 00:00:00 GMT
Link: <https://api.example.com/changelog>; rel="deprecation"  
4) Rate limiting: headers and 429

Expose limits and retry hints.

HTTP/1.1 429 Too Many Requests
Retry-After: 30
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1700001234
{
  "error": { "code": "rate_limited", "message": "Try again in 30 seconds" }
}
5) Webhooks: signatures, retries, idempotency

Send an event with an HMAC signature, include a unique event ID, and retry with exponential backoff.

# Event payload (POST to subscriber)
{
  "id": "evt_9f3a",
  "type": "order.created",
  "occurred_at": "2026-01-21T10:00:00Z",
  "data": { "order_id": "ord_123", "amount": 4999 }
}

# Headers
X-Signature: t=1705831200,v1=1c2b...  # HMAC-SHA256 over timestamp + body
Idempotency-Key: evt_9f3a

Subscriber verifies the signature, stores processed event IDs, and returns 2xx only after durable processing.

6) Multi-tenant scoping: header vs. path

Two common patterns (choose one and be consistent):

# Path scoping
GET /tenants/{tenant_id}/orders

# Header scoping
GET /orders
X-Tenant-Id: tnt_45

Enforce row-level filters in the service layer and, ideally, at the database policy level as a defense-in-depth measure.

Drills and exercises

Common mistakes and debugging tips

  • Mixing verbs in paths: Avoid /getOrder. Use GET /orders/{id}.
  • Changing response shapes without versioning: Add fields instead of renaming; if renaming is required, version it.
  • Ignoring pagination: Large lists will time out. Add page or cursor pagination early.
  • Weak webhook security: Always verify signatures and timestamps; require HTTPS; store and dedupe events.
  • One-size-fits-all rate limits: Apply limits per API key/tenant and consider different limits for read vs write.
  • Leaky multi-tenancy: Missing tenant filters cause data exposure. Enforce at service and data layers.
Debugging tips
  • Log correlation IDs in gateway and services to trace a request across hops.
  • Record effective limits and remaining tokens in logs to investigate 429 spikes.
  • Capture webhook signature base string and HMAC hex for quick local verification.
  • Maintain contract tests that load real responses and verify shape, types, and optionality.

Mini project: Orders API with webhooks and quotas

Build a small Orders API that supports resource modeling, pagination, rate limiting, and webhooks.

  1. Model users, orders, and order-items with predictable paths.
  2. Add pagination and filtering by status to the orders list.
  3. Return standard error objects for validation failures.
  4. Implement a token-bucket rate limit for POST /orders and expose X-RateLimit-* headers.
  5. Emit an order.created webhook with HMAC signature and retry on failure (at-least-once).
  6. Add tenant scoping via X-Tenant-Id and enforce row-level access.
  7. Provide a v2 header version that adds an optional field without breaking v1.
Hints
  • Choose either URL or header versioning and stay consistent.
  • Keep webhook handlers idempotent using the event ID.
  • Prefer cursor pagination if new items are frequently added.

Practical project ideas

  • Payments-like API: charges, refunds, webhooks for charge.succeeded and charge.failed
  • Issue tracker API: issues, comments, labels; cursor pagination and search filters
  • Analytics export API: async jobs with job.created webhooks and signed download URLs

Next steps

  • Complete the drills and the mini project.
  • Take the skill exam below to validate your understanding.
  • Refactor one of your existing APIs to improve versioning and error consistency.

API Design And Architecture — Skill Exam

This exam checks your understanding of API design and architecture: modeling, versioning, compatibility, rate limits, async/webhooks, gateways, and multi-tenant design.Rules: multiple-choice and multi-select questions. You can take it for free, unlimited attempts. A score of 70% or higher is a pass.Progress saving: anyone can take the exam; only logged-in users have their progress and results saved.

12 questions70% to pass

Have questions about API Design And Architecture?

AI Assistant

Ask questions about this tool