A self-hosted test lab for debugging redirects, caching, timeouts, and HTTP headers. Like httpbin, but focused on CDN/edge behavior.
Option 1: Use the hosted instance (zero setup)
curl -s https://probeopslab.com/debug.json | jq '{ip: .client_ip, country: .country}'Option 2: Self-host (for internal networks, CI/CD, or reproducing production behavior)
git clone https://github.com/kumarprobeops/probeopslab.git
cd probeopslab
docker compose up -dOpen http://localhost:8000 - done.
- Test against your own infrastructure - Debug issues in internal networks, staging environments, or behind corporate firewalls
- No external dependencies - Run tests in CI/CD pipelines without hitting external services
- Reproduce production behavior - Run it behind your own LB/WAF/CDN to test real header/redirect/cache behavior
- Full control - No rate limits, no third-party dependencies, no surprises
| Path | Description |
|---|---|
/debug |
Your IP, geo headers, request info |
/debug.json |
Same as above, JSON format for scripts |
/echo |
Request info + response headers (X-Request-Id, X-Client-IP, etc.) |
/r/301, /r/302, /r/307, /r/308 |
Redirect with specific status code |
/status/{code} |
Return specific HTTP status (200, 404, 500, etc.) |
/delay/{ms} |
Respond after N milliseconds |
/size/{bytes} |
Return N-byte response body |
/cache/* |
Various Cache-Control header configurations |
/use-cases |
Real-world troubleshooting scenarios |
| Mode | Access | Use Case |
|---|---|---|
| Development | localhost:8000 (app direct) |
Local testing, hot-reload |
| Production | :80/:443 (nginx → app) |
SSL termination, rate limiting |
- A server with Docker and Docker Compose installed
- A domain name pointing to your server's IP
- Ports 80 and 443 open
git clone https://github.com/kumarprobeops/probeopslab.git
cd probeopslab
cp .env.example .envEdit .env:
DOMAIN=yourdomain.com
LE_EMAIL=your-email@example.comFirst, start with the dev config to verify everything works:
docker compose up -d
curl http://yourdomain.com/debugOnce HTTP is working, use the init script:
./certbot/scripts/init-cert.shOr manually:
mkdir -p certbot/www
docker compose -f docker-compose.yml up -d nginx app
docker compose run --rm certbot certonly \
--webroot \
--webroot-path=/var/www/certbot \
--email your-email@example.com \
--agree-tos \
--no-eff-email \
-d yourdomain.com \
-d www.yourdomain.com
docker compose exec nginx nginx -s reloadcurl -I https://yourdomain.com/debugThe nginx container automatically reloads every 6 hours. Set up a cron job for renewal:
# Add to crontab (crontab -e)
0 0 * * * cd /path/to/probeopslab && docker compose run --rm certbot renew --quietIf you're putting this behind Cloudflare (recommended for production), there are two SSL options:
- Follow the Let's Encrypt setup above
- In Cloudflare dashboard: SSL/TLS > Overview > Set to "Full (strict)"
- Enable the orange cloud (proxy) on your DNS records
Cloudflare Origin Certificates are free, valid for 15 years, and simpler to manage:
- In Cloudflare dashboard: SSL/TLS > Origin Server > Create Certificate
- Copy the certificate and private key
- Save them to your server:
mkdir -p cloudflare
nano cloudflare/fullchain.pem # Paste certificate
nano cloudflare/privkey.pem # Paste private key-
The
cloudflare/directory is already mounted into nginx at/etc/nginx/cloudflare/(see docker-compose.yml) -
Update
nginx/snippets/ssl.confto use Cloudflare certs:
ssl_certificate /etc/nginx/cloudflare/fullchain.pem;
ssl_certificate_key /etc/nginx/cloudflare/privkey.pem;- In Cloudflare dashboard: SSL/TLS > Overview > Set to "Full (strict)"
- Enable orange cloud (proxy) on DNS records
When proxied through Cloudflare, your /debug endpoint will show additional headers:
cf-ray- Unique request IDcf-ipcountry- Visitor's country codecf-connecting-ip- Visitor's real IPcf-ipcity,cf-region- Geo data (Business/Enterprise plans)
This is a stateless debugging tool with minimal attack surface:
- No cookies or sessions - Each request is independent
- No data storage - Nothing is persisted, no database
- Header allowlist -
/debugonly exposes safe headers (host, user-agent, geo headers). Auth headers, cookies, and tokens are never shown. - Rate limiting - Default 10 req/s per IP (burst 20) in production nginx config
- No tracking - No analytics, no third-party scripts
Safe to run in corporate networks.
probeopslab/
├── app/
│ ├── main.py # FastAPI routes
│ ├── templates/ # Jinja2 HTML templates
│ ├── static/ # CSS, assets
│ ├── Dockerfile
│ └── requirements.txt
├── nginx/
│ ├── nginx.conf.template # Production config (HTTPS)
│ ├── nginx.dev.conf # Dev config (HTTP only)
│ └── snippets/
│ └── ssl.conf # SSL certificate paths
├── certbot/
│ ├── Dockerfile
│ └── scripts/
│ ├── init-cert.sh # First-time cert issuance
│ └── renew-cert.sh # Renewal script
├── cloudflare/ # Cloudflare Origin certs (if using)
├── docker-compose.yml # Production config
├── docker-compose.override.yml # Dev overrides (auto-loaded)
└── .env.example # Environment template
| Variable | Description | Default |
|---|---|---|
DOMAIN |
Your domain name | localhost |
LE_EMAIL |
Email for Let's Encrypt notifications | required |
The production config includes:
- Rate limiting: 10 req/s per IP (burst 20)
- Gzip compression
- Security headers (X-Frame-Options, X-Content-Type-Options, etc.)
- HTTP/2 enabled
- www to apex redirect
Adjust in nginx/nginx.conf.template as needed.
# Start development (HTTP, hot-reload)
docker compose up -d
# View logs
docker compose logs -f app
# Rebuild after code changes
docker compose up -d --build app
# Start production (HTTPS)
docker compose -f docker-compose.yml up -d
# Renew SSL certificate
docker compose run --rm certbot renew
docker compose exec nginx nginx -s reload
# Check nginx config
docker compose exec nginx nginx -tCertificate issuance fails
- Ensure port 80 is open and reachable
- Check DNS is pointing to your server
- Verify
.well-known/acme-challenge/is accessible
502 Bad Gateway
- Check if app container is running:
docker compose ps - Check app logs:
docker compose logs app
Cloudflare shows 525/526 errors
- SSL mode should be "Full (strict)" not "Flexible"
- Certificate must be valid (Let's Encrypt or Origin CA)
PRs welcome. Keep it simple - this is a utility, not a framework.
MIT