Cloudflare Setup
CloakProbe is designed to run behind Cloudflare. This guide covers the recommended setup.
Architecture
Section titled “Architecture”Internet → Cloudflare → Nginx → CloakProbe (localhost:8080)Or without Nginx:
Internet → Cloudflare → CloakProbe (0.0.0.0:8080, firewall restricted)Cloudflare Configuration
Section titled “Cloudflare Configuration”-
Add your domain to Cloudflare
Add your domain (e.g.,
ip.example.com) to Cloudflare and update your nameservers. -
Create DNS record
Add an A or AAAA record pointing to your server:
Type Name Content Proxy A ip your.server.ipProxied (orange cloud) -
SSL/TLS settings
In SSL/TLS → Overview, set encryption mode to:
- Full (strict) - Recommended if you have a valid certificate on your origin
- Full - If using a self-signed certificate
-
Enable useful features (optional)
- Speed → Optimization → Enable Brotli compression
- Security → Settings → Set security level to Medium or High
- Caching → Configuration → Disable caching or set to “Bypass” for API routes
How CloakProbe Uses Cloudflare Headers
Section titled “How CloakProbe Uses Cloudflare Headers”When proxied through Cloudflare, these headers are automatically added:
| Header | Description | Used for |
|---|---|---|
CF-Connecting-IP | Real client IP | Primary IP detection |
CF-Ray | Request ID | Debugging, shown in UI |
CF-IPCountry | Client country | Display (2-letter code) |
CF-Visitor | Connection protocol | TLS detection |
CDN-Loop | Loop detection | - |
CloakProbe reads CF-Connecting-IP first to get the real client IP, not Cloudflare’s IP.
Cloudflare Worker Setup (Advanced)
Section titled “Cloudflare Worker Setup (Advanced)”To get extended Cloudflare data (geo location, network info, security scores, etc.), you can use a Cloudflare Worker to forward request.cf data to your origin server as custom headers.
Why Use a Cloudflare Worker?
Section titled “Why Use a Cloudflare Worker?”The standard Cloudflare proxy provides basic headers like CF-Connecting-IP and CF-Ray. However, Cloudflare Workers have access to the request.cf object, which contains much more detailed information:
- Geo Location: Country, city, region, latitude/longitude, timezone
- Network: ASN, AS organization, colo (datacenter)
- Connection: HTTP protocol, TLS version, TLS cipher
- Security: Trust score, bot score, verified bot status
By forwarding this data as custom headers (X-CF-*), CloakProbe can display all this information in both the HTML UI and API responses.
Step-by-Step Setup
Section titled “Step-by-Step Setup”-
Create a new Worker application
In the Cloudflare dashboard, go to Workers & Pages → Create application → Create Worker.
-
Use the Hello World template
Click Start with Hello World! to create a basic Worker.
-
Replace with the example script
Replace the default code with the example Worker script below.
-
Deploy the Worker
Click Deploy to save and deploy your Worker.
-
Create a Worker Route
Go to Workers & Pages → Your Worker → Triggers → Routes → Add route.
- Route:
your-domain.com/*(orip.your-domain.com/*) - Zone: Select your domain
- Click Add route
- Route:
-
Configure DNS records
Ensure your DNS records are set to Proxied (orange cloud) so the Worker can intercept requests.
Example Worker Code
Section titled “Example Worker Code”Here’s a complete example Worker that extracts data from request.cf and forwards it to your origin server:
/** * Cloudflare data forwarder for CloakProbe * * This Worker extracts information from the request.cf object and forwards * it to the origin server as custom headers (X-CF-*). CloakProbe will * automatically parse and display these headers. */export default { async fetch(request, env, ctx) { // Preserve the original URL const url = new URL(request.url);
// Extract information from the request.cf object // This object contains detailed Cloudflare data about the request const cf = request.cf || {};
// Create new headers by copying the original request headers const newHeaders = new Headers(request.headers);
// Add Geo Location headers from request.cf if (cf.country) newHeaders.set('X-CF-Country', cf.country); if (cf.city) newHeaders.set('X-CF-City', cf.city); if (cf.region) newHeaders.set('X-CF-Region', cf.region); if (cf.regionCode) newHeaders.set('X-CF-Region-Code', cf.regionCode); if (cf.continent) newHeaders.set('X-CF-Continent', cf.continent); if (cf.latitude) newHeaders.set('X-CF-Latitude', cf.latitude); if (cf.longitude) newHeaders.set('X-CF-Longitude', cf.longitude); if (cf.postalCode) newHeaders.set('X-CF-Postal-Code', cf.postalCode); if (cf.timezone) newHeaders.set('X-CF-Timezone', cf.timezone);
// Add Network headers from request.cf if (cf.asn) newHeaders.set('X-CF-ASN', cf.asn.toString()); if (cf.asOrganization) newHeaders.set('X-CF-AS-Organization', cf.asOrganization); if (cf.colo) newHeaders.set('X-CF-Colo', cf.colo);
// Add Connection headers from request.cf if (cf.httpProtocol) newHeaders.set('X-CF-HTTP-Protocol', cf.httpProtocol); if (cf.tlsVersion) newHeaders.set('X-CF-TLS-Version', cf.tlsVersion); if (cf.tlsCipher) newHeaders.set('X-CF-TLS-Cipher', cf.tlsCipher);
// Add Security headers from request.cf if (cf.clientTrustScore !== undefined) { newHeaders.set('X-CF-Trust-Score', cf.clientTrustScore.toString()); }
// Add Bot Management headers (if Bot Management is enabled) if (cf.botManagement) { if (cf.botManagement.score !== undefined) { newHeaders.set('X-CF-Bot-Score', cf.botManagement.score.toString()); } if (cf.botManagement.verifiedBot !== undefined) { newHeaders.set('X-CF-Verified-Bot', cf.botManagement.verifiedBot.toString()); } }
// Create a new request with the modified headers // This preserves the original request method, body, etc. const modifiedRequest = new Request(request, { headers: newHeaders });
// Forward the modified request to the origin server return fetch(modifiedRequest); }};How It Works
Section titled “How It Works”-
Request interception: The Worker intercepts all requests to your domain (via the Worker Route).
-
Data extraction: The Worker reads data from
request.cf, which contains Cloudflare’s detailed information about the request. -
Header forwarding: The Worker adds custom headers (X-CF-*) containing this data and forwards the request to your origin server.
-
CloakProbe processing: CloakProbe receives these headers, sanitizes them, and displays them in:
- HTML UI: Organized into sections (Geo Location, Network, Connection, Security)
- JSON API: Under the
cloudflarefield - Plain text API: In organized sections
Verifying the Setup
Section titled “Verifying the Setup”After setting up the Worker, verify it’s working:
# Check that custom headers are being receivedcurl -v https://your-domain.com/api/v1/info 2>&1 | grep -i "x-cf-"
# Check JSON response for cloudflare fieldcurl -s https://your-domain.com/api/v1/info | jq '.cloudflare'You should see:
- Custom X-CF-* headers in the request
cloudflarefield in the JSON response with geo, network, connection, and security data- Enhanced information displayed in the HTML UI
Troubleshooting
Section titled “Troubleshooting”Worker not intercepting requests:
- Ensure the Worker Route matches your domain pattern (e.g.,
your-domain.com/*) - Verify DNS records are proxied (orange cloud)
- Check that the Worker is deployed and active
Headers not appearing:
- Verify the Worker code is correctly extracting from
request.cf - Check that the origin server is receiving the X-CF-* headers
- Ensure CloakProbe version is 0.1.1 or later
Missing data:
- Some fields in
request.cfmay beundefinedfor certain requests - Bot Management data requires Bot Management to be enabled in Cloudflare
- Geo location accuracy depends on Cloudflare’s data
Firewall Rules
Section titled “Firewall Rules”UFW (Ubuntu/Debian)
Section titled “UFW (Ubuntu/Debian)”Allow only Cloudflare IPs to reach your server:
# Cloudflare IPv4 rangesfor ip in 173.245.48.0/20 103.21.244.0/22 103.22.200.0/22 103.31.4.0/22 \ 141.101.64.0/18 108.162.192.0/18 190.93.240.0/20 188.114.96.0/20 \ 197.234.240.0/22 198.41.128.0/17 162.158.0.0/15 104.16.0.0/13 \ 104.24.0.0/14 172.64.0.0/13 131.0.72.0/22; do sudo ufw allow from $ip to any port 443done
# Block direct accesssudo ufw deny 443iptables
Section titled “iptables”# Allow Cloudflare IPs (example)iptables -A INPUT -p tcp --dport 443 -s 173.245.48.0/20 -j ACCEPTiptables -A INPUT -p tcp --dport 443 -s 103.21.244.0/22 -j ACCEPT# ... add all Cloudflare ranges
# Drop other traffic to 443iptables -A INPUT -p tcp --dport 443 -j DROPRate Limiting
Section titled “Rate Limiting”Configure rate limiting in Cloudflare:
-
Go to Security → WAF → Rate limiting rules
-
Create a rule:
- If: URI Path contains
/api/ - Then: Block for 1 minute
- When rate exceeds: 100 requests per 10 seconds
- If: URI Path contains
Page Rules (Optional)
Section titled “Page Rules (Optional)”Create page rules for specific behaviors:
Disable caching for API
Section titled “Disable caching for API”- URL:
ip.example.com/api/* - Setting: Cache Level = Bypass
Force HTTPS
Section titled “Force HTTPS”- URL:
ip.example.com/* - Setting: Always Use HTTPS
Verifying Setup
Section titled “Verifying Setup”Check that Cloudflare headers are being received:
curl -v https://ip.example.com/api/v1/info 2>&1 | grep -i "cf-"In the JSON response, you should see:
connection.cf_ray- Cloudflare Ray IDconnection.datacenter- Cloudflare datacenter code
Troubleshooting
Section titled “Troubleshooting”IP shows Cloudflare’s IP instead of client
Section titled “IP shows Cloudflare’s IP instead of client”Ensure CloakProbe is reading CF-Connecting-IP. Check:
- The domain is proxied (orange cloud) in DNS
- You’re accessing via the domain, not directly by IP
520/521/522 errors
Section titled “520/521/522 errors”- 520: CloakProbe returned an empty or invalid response
- 521: CloakProbe is not running or port is blocked
- 522: Connection timed out - check firewall rules
SSL certificate errors
Section titled “SSL certificate errors”For Full (strict) mode, ensure your origin has a valid certificate. Options:
- Use Cloudflare Origin CA certificate
- Use Let’s Encrypt certificate
- Use Cloudflare Tunnel instead