Design, build, test, document, and secure production-grade APIs. Covers the full lifecycle from schema design through deployment, monitoring, and versioning. Use when designing new APIs, reviewing existing ones, generating OpenAPI specs, building test suites, or debugging production issues.
Instalar com Codex ou Claude Copie este prompt, cole no Codex, Claude ou outro assistente e deixe que ele revise a página da skill e instale para você.
Um comando direto ignora o prompt de revisão. Verifique a origem antes de executá-lo.
Instruções da origem · Visualização somente leitura
name
afrexai-api-architect
description
Design, build, test, document, and secure production-grade APIs. Covers the full lifecycle from schema design through deployment, monitoring, and versioning. Use when designing new APIs, reviewing existing ones, generating OpenAPI specs, building test suites, or debugging production issues.
API Architect — Full Lifecycle API Development
Design, build, test, document, secure, and monitor production-grade APIs. Not just curl commands — a complete engineering methodology.
When to Use
Designing a new API (REST, GraphQL, or gRPC)
Reviewing an existing API for quality, consistency, or security
Generating or validating OpenAPI/Swagger specs
Building comprehensive test suites (unit, integration, contract, load)
Debugging production API issues
Planning API versioning and deprecation
Setting up monitoring, rate limiting, and error handling
Phase 1: API Design
Design-First Approach
Always design before coding. The spec IS the contract.
Need to... → Method Idempotent? Safe?
Get a resource or collection → GET Yes Yes
Create a new resource → POST No No
Full replace of a resource → PUT Yes No
Partial update of a resource → PATCH No* No
Remove a resource → DELETE Yes No
Check if resource exists → HEAD Yes Yes
List allowed methods → OPTIONS Yes Yes
* PATCH can be idempotent if using JSON Merge Patch
Status Code Decision Tree
Success?
├── Created something new? → 201 Created (Location header)
├── Accepted for async processing? → 202 Accepted (include status URL)
├── No body to return? → 204 No Content
└── Returning data? → 200 OK
Client error?
├── Malformed request syntax? → 400 Bad Request
├── No/invalid credentials? → 401 Unauthorized
├── Valid credentials but insufficient permissions? → 403 Forbidden
├── Resource doesn't exist? → 404 Not Found
├── Method not allowed on resource? → 405 Method Not Allowed
├── Conflict with current state? → 409 Conflict
├── Resource permanently gone? → 410 Gone
├── Validation failed? → 422 Unprocessable Entity
├── Too many requests? → 429 Too Many Requests (Retry-After header)
└── Precondition failed (etag mismatch)? → 412 Precondition Failed
Server error?
├── Unexpected failure? → 500 Internal Server Error
├── Upstream dependency failed? → 502 Bad Gateway
├── Temporarily overloaded? → 503 Service Unavailable (Retry-After)
└── Upstream timeout? → 504 Gateway Timeout
Request/Response Design
Standard Response Envelope
// Success (single resource){"data":{"id":"ord_abc123","status":"confirmed", ... },"meta":{"request_id":"req_xyz789"}}// Success (collection){"data":[ ... ],"meta":{"request_id":"req_xyz789"},"pagination":{"total":142,"page":2,"per_page":20,"total_pages":8,"next":"/api/v1/orders?page=3&per_page=20","prev":"/api/v1/orders?page=1&per_page=20"}}// Error{"error":{"code":"VALIDATION_FAILED","message":"Request validation failed","details":[{"field":"email","message":"Must be a valid email address","code":"INVALID_FORMAT"},{"field":"age","message":"Must be at least 18","code":"MIN_VALUE","min":18}]},"meta":{"request_id":"req_xyz789"}}
Pagination Patterns — When to Use Which
Pattern
Use When
Pros
Cons
Offset?page=2&per_page=20
Simple UI pagination, small datasets
Easy to implement, page jumping
Drift on inserts, slow on large offsets
Cursor?after=eyJ...&limit=20
Infinite scroll, real-time feeds, large datasets
Consistent, performant
No page jumping, opaque cursors
Keyset?created_after=2024-01-01&limit=20
Time-series data, logs
Fast, transparent
Requires sortable field, no count
Filtering, Sorting, Field Selection
# Filtering
GET /orders?status=active&created_after=2024-01-01&total_min=100
# Sorting (prefix - for descending)
GET /orders?sort=-created_at,total
# Field selection (reduce payload)
GET /orders?fields=id,status,total,customer.name
# Search
GET /products?q=wireless+headphones
# Combined
GET /orders?status=active&sort=-created_at&fields=id,status,total&page=1&per_page=10
Phase 2: OpenAPI Specification
Generate OpenAPI 3.1 Spec
For each resource in your design, generate a complete spec:
Validation Order:
1. Content-Type header (reject non-JSON early)
2. Authentication (401 before wasting cycles)
3. Authorization (403 - does this user have access?)
4. Path parameters (404 - does the resource exist?)
5. Query parameters (400 - valid types/ranges?)
6. Request body schema (422 - valid structure?)
7. Business rules (422 - valid state transition?)
Error Handling — Standard Error Codes
Define a consistent error code enum for your API:
# Authentication & Authorization
AUTH_REQUIRED — No credentials provided
AUTH_INVALID — Invalid/expired credentials
AUTH_INSUFFICIENT — Valid credentials, wrong permissions
AUTH_RATE_LIMITED — Too many auth attempts
# Validation
VALIDATION_FAILED — Generic validation error (see details array)
INVALID_FORMAT — Field format wrong (email, UUID, etc.)
REQUIRED_FIELD — Required field missing
OUT_OF_RANGE — Value outside allowed range
INVALID_ENUM — Value not in allowed set
# Resource
NOT_FOUND — Resource doesn't exist
ALREADY_EXISTS — Duplicate (unique constraint)
CONFLICT — State conflict (e.g., already cancelled)
GONE — Resource permanently deleted
# Business Logic
INSUFFICIENT_FUNDS — Payment-related
QUOTA_EXCEEDED — Usage limit reached
FEATURE_DISABLED — Feature flag off
DEPENDENCY_FAILED — Upstream service error
# System
INTERNAL_ERROR — Unexpected server error
SERVICE_UNAVAILABLE — Temporarily down
TIMEOUT — Request took too long
Idempotency
For non-idempotent operations (POST), require an idempotency key:
Request:
POST /orders
Idempotency-Key: ord_req_abc123
Server behavior:
1. Check if Idempotency-Key was seen before
2. If yes → return cached response (same status, same body)
3. If no → process request, cache response for 24h
4. Key format: client-generated UUID or meaningful string
Rate Limiting
Standard headers to include:
X-RateLimit-Limit: 100 # Max requests per window
X-RateLimit-Remaining: 67 # Remaining in current window
X-RateLimit-Reset: 1706886400 # Unix timestamp when window resets
Retry-After: 30 # Seconds to wait (on 429)
# === Setup ===
BASE="https://api.example.com/v1"
TOKEN="your_bearer_token"alias api='curl -s -H "Authorization: Bearer $TOKEN" -H "Content-Type: application/json"'# === CRUD Lifecycle Test ===# Create
ORDER=$(api -X POST "$BASE/orders" -d '{"customer_id":"cust_1","items":[{"product_id":"prod_1","qty":2}]}')
ORDER_ID=$(echo"$ORDER" | jq -r '.data.id')
echo"Created: $ORDER_ID"# Read
api "$BASE/orders/$ORDER_ID" | jq .
# Update
api -X PATCH "$BASE/orders/$ORDER_ID" -d '{"notes":"Rush order"}' | jq .
# List with filters
api "$BASE/orders?status=draft&sort=-created_at&per_page=5" | jq .
# Action (state transition)
api -X POST "$BASE/orders/$ORDER_ID/confirm" | jq .
# Delete
curl -s -o /dev/null -w "%{http_code}" -X DELETE -H "Authorization: Bearer $TOKEN""$BASE/orders/$ORDER_ID"# === Error Testing ===# No auth
curl -s "$BASE/orders" | jq .error
# Invalid body
api -X POST "$BASE/orders" -d '{"invalid": true}' | jq .error
# Not found
api "$BASE/orders/nonexistent" | jq .error
# === Performance ===# Timing breakdown
curl -s -o /dev/null -w "DNS:%{time_namelookup} TCP:%{time_connect} TLS:%{time_appconnect} TTFB:%{time_starttransfer} Total:%{time_total}\n" -H "Authorization: Bearer $TOKEN""$BASE/orders"# Quick load test (50 requests, 10 concurrent)seq 50 | xargs -P10 -I{} curl -s -o /dev/null -w "%{http_code} %{time_total}s\n" -H "Authorization: Bearer $TOKEN""$BASE/orders"
Contract Testing
Validate your API hasn't broken backward compatibility:
# contract-tests.yamlcontract:name:OrderAPIContractversion:1.0.0rules:# These changes are SAFE (non-breaking)safe:-Addingnewoptionalfieldstoresponses-Addingnewendpoints-Addingnewoptionalqueryparameters-Addingnewenumvalues(ifclientshandleunknown)-Widening a constraint (min:5→min:1)# These changes are BREAKINGbreaking:-Removingaresponsefield-Renamingaresponsefield-Changingafieldtype-Addinganewrequiredrequestfield-Removinganendpoint-Narrowing a constraint (max:100→max:50)-Changingerrorresponseformat-Removinganenumvalue# Verify after every changechecks:-Allexistingfieldsstillpresentinresponses-Allexistingfieldtypesunchanged-Allexistingrequiredfieldsstillrequired(nomore,nofewer)-Defaultvaluesunchanged-Errorformatunchanged
# Restrictive (recommended)cors:origins:-https://app.example.com-https://admin.example.commethods: [GET, POST, PUT, PATCH, DELETE]
headers: [Authorization, Content-Type, X-Request-ID]
credentials:truemax_age:3600# Common mistakes to avoid:# ❌ Access-Control-Allow-Origin: * (with credentials)# ❌ Reflecting Origin header without validation# ❌ Allowing all methods/headers
Phase 6: Versioning & Deprecation
Versioning Strategy Decision
Strategy
Example
Pros
Cons
Use When
URL path
/v1/orders
Explicit, easy routing
URL pollution
Public APIs, multiple major versions
Header
API-Version: 2024-01
Clean URLs
Hidden, harder to test
Internal APIs
Query param
?version=2
Easy to test
Pollutes params
Quick prototypes
Date-based
2024-01-15
Clear timeline
Many versions
Stripe-style APIs
Recommended: URL path for major versions, header for minor variations.
Deprecation Playbook
Timeline:
1. T+0: Announce deprecation (docs, changelog, email)
2. T+0: Add Deprecation + Sunset headers to old endpoints
3. T+30d: Log warnings for old endpoint usage
4. T+60d: Email heavy users of old endpoint directly
5. T+90d: Return 299 warning header
6. T+180d: Shut down old endpoint (410 Gone)
Headers:
Deprecation: true
Sunset: Sat, 01 Jun 2025 00:00:00 GMT
Link: <https://api.example.com/v2/orders>; rel="successor-version"
Migration Guide Template
# Migrating from v1 to v2## Breaking Changes1.`user.name` split into `user.first_name` + `user.last_name`2. Pagination changed from offset to cursor-based
3. Error format updated (see new schema)
## Step-by-Step Migration1. Update your client SDK to v2 (`npm install @example/sdk@2`)
2. Update response parsing for split name fields
3. Replace `?page=N` with `?after=cursor` pagination
4. Update error handling for new error format
## Compatibility Mode
Set `X-Compat-Mode: v1` header to get v1-style responses from v2 endpoints.
Available until 2025-06-01.
// GET /health — for load balancers (simple){"status":"ok"}// GET /health/detailed — for monitoring (authenticated){"status":"degraded","version":"1.5.2","uptime_seconds":86400,"checks":{"database":{"status":"ok","latency_ms":5},"redis":{"status":"ok","latency_ms":2},"external_payment_api":{"status":"degraded","latency_ms":2500,"error":"timeout"},"disk":{"status":"ok","free_gb":45.2}}}
Phase 8: API Review Scoring
When reviewing an existing API, score across these dimensions:
API Quality Rubric (0-100)
Dimension
Weight
Criteria
Score
Design Consistency
20%
Naming conventions, HTTP methods, status codes, URL structure
/20
Documentation
15%
OpenAPI spec, examples, error docs, changelog
/15
Error Handling
15%
Consistent format, helpful messages, proper codes, no leakage