Skip to content
API Versioning: Evolving APIs Without Breaking Clients 3 min

API Versioning: Evolving APIs Without Breaking Clients

SD
ScaleDojo
May 11, 2026
3 min read781 words
1
API Versioning: Evolving APIs Without Breaking Clients

The Problem

In 2012, Twitter changed their API from v1 to v1.1 and gave developers nine months to migrate. Even with that generous timeline, thousands of third-party apps broke on the deadline. Some developers had abandoned their apps. Some missed the announcement. Some did not have time to test. The Twitter developer community was furious. API versioning is not just a technical decision - it is a social contract with everyone who depends on your API.

The Three Main Strategies

1. URL Path Versioning (Most Common)

The most explicit and widely adopted approach:

API Versioning: Evolving APIs Without Breaking Clients - Architecture Diagram
Architecture overview
GET /v1/users/42    <-- Original version
GET /v2/users/42    <-- Breaking changes in user response

# Who uses this:
# Stripe:    https://api.stripe.com/v1/charges
# GitHub:    https://api.github.com/v3/repos
# Twilio:    https://api.twilio.com/2010-04-01/Accounts

Pros: crystal clear which version you are using. Easy to route in load balancers. Easy to test (paste URL in browser). Can run v1 and v2 on completely different servers.

Cons: pollutes URLs, makes it harder to maintain multiple versions of internal logic. Purists argue the URL should identify the resource, not the API version.

2. Header Versioning

GET /users/42
Accept: application/vnd.myapi.v2+json

# Or a custom header:
GET /users/42
X-API-Version: 2

# Who uses this:
# GitHub (also): Accept: application/vnd.github.v3+json

Pros: clean URLs, version is metadata not part of the resource identity.

Cons: harder to test (cannot just paste URL in browser), less discoverable, some proxy caches ignore custom headers.

3. Query Parameter Versioning

GET /users/42?version=2

# Who uses this:
# Google APIs: ?v=3
# Amazon: ?Version=2012-11-05

Pros: easy to test, optional (can default to latest or oldest).

Cons: messy with other query parameters, caching gets complicated because the version changes the cache key.

Comparison at a Glance

Strategy        Clarity   Cacheable   Testable   Used By
--------------  --------  ----------  ---------  ----------------
URL path        High      Yes         Yes        Stripe, Twilio
Header          Medium    Varies      No*        GitHub
Query param     Medium    Careful     Yes        Google, AWS
Date-based      High      Yes         Yes        Twilio, Stripe

* Requires curl or Postman to test with custom headers

The Practical Recommendation

For most teams: use URL path versioning (/v1/, /v2/). It is the most widely understood pattern, works with every tool, and makes it impossible to accidentally call the wrong version.

But do not version every change. Only create a new version when you make a BREAKING change:

BREAKING changes (require new version):
  - Removing a field from the response
  - Changing a field's type (string -> integer)
  - Renaming a field (user_name -> username)
  - Changing response structure ({"users": [...]} -> [{...}])
  - Changing error format
  - Making a previously optional field required

NON-BREAKING changes (backwards compatible, no new version needed):
  + Adding a new optional field to the response
  + Adding a new endpoint
  + Adding a new optional query parameter
  + Adding a new optional request body field
  + Adding new enum values (if clients handle unknown values)
  + Adding new error codes (if clients have a default handler)

Deprecation Strategy

When releasing v2, follow this playbook:

  1. Announce deprecation of v1 with a timeline (e.g., 12 months). Post in changelog, send emails, show in dashboard.
  2. Add a Sunset header to v1 responses indicating the shutdown date: Sunset: Sat, 01 Mar 2026 00:00:00 GMT
  3. Add a Deprecation header: Deprecation: true
  4. Monitor v1 usage analytics. Identify your top 20 consumers by volume and reach out directly.
  5. Start returning warning headers on v1: Warning: 299 - 'API v1 will be retired on 2026-03-01. Please migrate to v2.'
  6. After the deprecation period, return 410 Gone with a body explaining how to migrate.

Stripe's Versioning: The Gold Standard

Stripe uses a unique date-based approach: each API key is pinned to a specific API version (e.g., 2024-06-20). Your integration keeps working even as Stripe releases updates. You upgrade at your own pace by changing the version in your dashboard. Every version difference is documented in their changelog. When you override the version in a request header, you can test the new version without affecting production. This is the most developer-friendly versioning strategy in the industry.

Interview Tip

When asked about API versioning in an interview, say: 'I use URL path versioning for clarity. I only bump versions for breaking changes like removing fields or changing types. Adding new optional fields is backwards-compatible and does not need a new version. For the deprecation timeline, I give clients 12 months with automated warnings in response headers, usage monitoring, and direct outreach to top consumers.' Then mention Stripe's date-based versioning as an advanced approach.

Key Takeaway

Version your API in the URL path. Only bump versions for breaking changes. Additive changes (new fields, new endpoints) are backwards-compatible and do not need a new version. Give clients generous deprecation timelines and include Sunset headers so automated tools can detect upcoming retirements.

Enjoyed this article?

Share it with your network to help others level up their system design skills.

Discussion0

Join the Discussion

Sign in to leave comments, reply to others, or like insights.

Sign In to ScaleDojo

No comments yet. Be the first to start the thread!

Related Articles

Enjoyed this content?

Your support keeps us creating free resources

We put a lot of hours into researching and writing these guides. If it helped you, consider buying us a coffee. Every bit goes toward keeping ScaleDojo's content free and growing.

$

One-time payment via Stripe. ScaleDojo account required.

ScaleDojo Logo
Initializing ScaleDojo