Working with API Authentication
1. Implementing API Keys
| Aspect | Detail |
| Format | Random 32+ bytes, base62/base64url |
| Prefix | sk_live_, pk_test_ for grep/leak detection |
| Storage | SHA-256 hashed in DB |
| Display | Show once at creation |
2. Implementing API Key Rotation
| Step | Detail |
| Dual keys | Allow two active keys per service |
| Issue new | Update consumer; both valid |
| Revoke old | After cutover window |
| Schedule | 90-day rotation |
3. Using OAuth 2.0 for APIs
| Grant | Use |
| Client credentials | M2M |
| Authorization code + PKCE | User-delegated |
| JWT bearer | Trusted client assertion |
| Token exchange | Service-to-service with user context |
4. Implementing Bearer Authentication
Example: Spring Resource Server
http.oauth2ResourceServer(o -> o.jwt(j ->
j.jwkSetUri("https://auth.example/.well-known/jwks.json")));
5. Using Basic Authentication for APIs
| When | Detail |
| Acceptable | Internal admin, M2M behind VPN |
| Avoid | Public APIs, mobile/web |
| Pair with | IP allowlist, mTLS |
6. Implementing Digest Authentication
Rarely used in modern APIs. Replace with Bearer/HMAC.
7. Using Mutual TLS
| Aspect | Detail |
| Setup | Server requires/verifies client cert |
| PKI | Internal CA, short-lived certs (SPIFFE/SPIRE) |
| Mesh | Istio/Linkerd handle automatically |
8. Implementing HMAC Signatures
Example: HMAC-SHA256 signing
const ts = Date.now();
const body = JSON.stringify(payload);
const sig = crypto.createHmac("sha256", secret)
.update(`${method}\n${path}\n${ts}\n${body}`).digest("base64");
headers["X-Timestamp"] = ts;
headers["X-Signature"] = sig;
9. Using AWS Signature V4
| Step | Detail |
| Canonical request | METHOD + URI + query + headers + payload-hash |
| String to sign | algorithm + date + scope + sha256(canonical) |
| Signing key | HMAC chain: secret → date → region → service → "aws4_request" |
| Header | Authorization: AWS4-HMAC-SHA256 Credential=...,Signature=... |
10. Implementing Rate Limiting by Identity
| Key | Detail |
| By API key | Tier-based quotas |
| By user | Authenticated user limits |
| By IP | Fallback for anonymous |
| Response | 429 + Retry-After, X-RateLimit-* headers |
11. Handling Authentication Errors
| Code | Use |
| 401 | Missing/invalid credentials |
| 403 | Authenticated but insufficient scope/permission |
| 429 | Rate limit exceeded |
| Body | RFC 7807 problem+json; never reveal internals |