Update project structure to use a src/ directory layout and improve documentation across multiple files. - Update README.md build command to use ./src - Add directory structure documentation - Update status endpoint to include DB health status - Add pagination support (limit/offset) to whitelist list endpoints - Document new query parameters with examples - Update deployment guide to mark API token as required - Add testing instructions - Clarify audit log rotation in design documentation
3.2 KiB
3.2 KiB
Auth-proxy Security Model
Authentication flow
- Client request arrives at NGINX.
- NGINX sends an internal auth_request subrequest to auth-proxy.
- Auth-proxy checks:
- Is the IP in the permanent whitelist? → Allow.
- Is the IP in the temporary whitelist and not expired? → Allow.
- Otherwise → 401 Unauthorized.
- NGINX passes the request to the upstream service if auth-proxy returned 200.
- NGINX returns 401 to the client if auth-proxy returned 401/403.
IP handling
Permanent whitelist
- Stored in SQLite
permanent_whitelisttable. - Only single IPs and CIDR ranges (as strings) are supported.
- Added/removed via the
/api/whitelist/permAPI.
Temporary whitelist
- Stored in SQLite
temp_whitelisttable. - Entries expire after their TTL.
- The cleanup goroutine runs every 60 seconds (configurable) to remove expired entries.
API key
The API key is the only secret for the /api/* endpoints. It's sent as a bearer token in the Authorization header.
- Required. The service will not start without it.
- Keep it secret. Don't log it. Don't put it in the URL.
- Use a strong random string.
- Rotate it regularly.
Audit log
All whitelist operations are logged to the audit_log table in SQLite.
Each entry records:
action— what happened (add_temp,delete_temp,add_perm,delete_perm,expire_temp)iporcidr— the affected IP or CIDRttl_seconds— for temp entriesreason— the reason providedapi_client_ip— the IP that made the API call (from NGINXX-Real-IP)
Retrieve logs via the /api/logs endpoint.
The audit log is automatically rotated to maintain a maximum of 100,000 entries.
IP validation
The /api/whitelist/temp and /api/whitelist/perm endpoints validate inputs:
/api/whitelist/temprequires a valid IP address./api/whitelist/permrequires a valid IP address or CIDR range.- Invalid inputs return
400 Bad Request.
Graceful shutdown
The service listens for SIGTERM and SIGINT. On signal:
- Stop accepting new connections.
- Close idle connections.
- Wait for in-flight requests to complete (up to 30 seconds).
- Exit.
This ensures Docker deployments can shut down cleanly.
What we don't do
- We don't support JWT/OAuth. If you need these, add them later.
- We don't support session state. The auth decision is made per-request.
- We don't support rate limiting. Use NGINX's limit_req for that.
- We don't support IP-based rate limiting. Use NGINX's limit_conn for that.
- We don't support IPv6. If you need IPv6, add it later.
- We don't support TLS. The auth endpoint should always be served over TLS.
- We don't support logging to a file. Logs go to stdout (Docker).
- We don't support metrics. If you need metrics, add them later.
- We don't support health checks with Prometheus. The /status endpoint returns a JSON response with uptime, DB status, and whitelist counts.
- We don't support configuration via a config file. Use environment variables.
- We don't support multiple domains. The auth-proxy service doesn't care about domains.
- We don't support HTTP/2. The auth-proxy service uses HTTP/1.1 only.
- We don't support WebSocket. The auth-proxy service doesn't need WebSocket.
- We don't support gRPC. The auth-proxy service is a simple REST API.