Add three new blog posts
This commit is contained in:
@@ -0,0 +1,72 @@
|
||||
---
|
||||
title: "REST API Design: Mistakes I've Made So You Don't Have To"
|
||||
date: 2026-05-13T09:00:00+08:00
|
||||
draft: false
|
||||
tags:
|
||||
- API
|
||||
- REST
|
||||
- Backend
|
||||
---
|
||||
|
||||
I've designed, built, and maintained enough REST APIs to have made most of the classic mistakes. Here's what I wish someone had told me upfront.
|
||||
|
||||
## 1. Versioning Early
|
||||
|
||||
Don't wait until you need it. Version your API from day one, either in the URL (`/v1/users`) or via the `Accept` header. Retrofitting versioning onto an unversioned API is painful for everyone involved.
|
||||
|
||||
My preference: **URL-based versioning**. It's visible, impossible to forget, and trivially cacheable.
|
||||
|
||||
## 2. Pagination by Default
|
||||
|
||||
Every list endpoint should be paginated. Every. Single. One.
|
||||
|
||||
```json
|
||||
{
|
||||
"data": [...],
|
||||
"pagination": {
|
||||
"cursor": "eyJpZCI6MTIzfQ==",
|
||||
"has_more": true,
|
||||
"total": 847
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
I've moved from offset-based to cursor-based pagination almost everywhere. Cursors handle real-time data changes gracefully and perform better on large datasets.
|
||||
|
||||
## 3. Error Responses Should Be Consistent
|
||||
|
||||
A predictable error shape means less client-side code:
|
||||
|
||||
```json
|
||||
{
|
||||
"error": {
|
||||
"code": "INSUFFICIENT_BALANCE",
|
||||
"message": "Account balance too low for this transaction",
|
||||
"details": {
|
||||
"required": 29.99,
|
||||
"available": 12.50
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Never expose stack traces in production. Never leak internal IDs without intent.
|
||||
|
||||
## 4. Idempotency Keys
|
||||
|
||||
For any mutating endpoint, support an `Idempotency-Key` header. Your payment team will thank you, and so will your users when a retry doesn't double-charge them.
|
||||
|
||||
## 5. Think in Terms of Deprecation
|
||||
|
||||
Add a `Deprecation` and `Sunset` header to old endpoints:
|
||||
|
||||
```
|
||||
Deprecation: true
|
||||
Sunset: Sat, 01 Aug 2026 00:00:00 GMT
|
||||
```
|
||||
|
||||
Give consumers time to migrate, then actually follow through on removal. Keeping deprecated endpoints around "just in case" is technical debt with interest.
|
||||
|
||||
---
|
||||
|
||||
Good API design is mostly about **empathy for the consumer**. Ask yourself: would *you* enjoy integrating with this?
|
||||
Reference in New Issue
Block a user