I've been tasked with evaluating our secure remote access setup for a critical finance team that needs near-instantaneous RDP access to internal trading and analytics workstations. The current solution is lagging, literally, and we're looking at Cloudflare Access as a potential zero-trust replacement for a traditional VPN. The primary metric here is latency, measured in milliseconds from initial request to usable desktop, followed by consistency.
I've run synthetic benchmarks simulating a user in Frankfurt connecting to a protected origin in London, testing various configurations. The goal is to minimize the added latency of the Access handshake and proxy while maintaining the security posture required for financial data. Here are the key findings and the configuration that yielded the lowest end-to-end latency.
**Optimal Configuration for Low-Latency RDP (Tunnel-based):**
* **Tunnel over Public Hostname:** Do NOT use a public IP on your origin server and rely solely on Access policies. Instead, deploy `cloudflared` as a daemon on the RDP host and create a Tunnel. This removes any public ingress points and reduces the network hop distance through Cloudflare's edge.
```yaml
# cloudflared config.yml for RDP host
tunnel: your-tunnel-uuid
credentials-file: /etc/cloudflared/credentials.json
ingress:
- hostname: rdp-finance.example.com
service: rdp://localhost:3389
originRequest:
proxyType: socks
- service: http_status:404
```
The `proxyType: socks` is critical for raw TCP traffic like RDP; the default HTTP proxy adds unnecessary overhead.
* **Session Duration & Auth Caching:** For frequent reconnects (e.g., dropped sessions), set `session_duration` in your Access policy to a reasonable but secure maximum, like 12 hours. This prevents repeated full authentication cycles. Combine this with short-lived certificates (mTLS) for the service itself.
```
# Policy snippet in your Access Group or Application config
session_duration = "12h"
```
* **Geolocation & Edge Routing:** Use `geo` rules in your Access policy to *allow* only necessary regions, but more importantly, this forces the user to the nearest Cloudflare edge that can connect to your Tunnel. We found that not using any `geo` rules sometimes led to suboptimal edge routing, adding 20-30ms. Be precise.
* **Disable "Browser Rendering" and "App Launcher":** In the Access application settings, ensure all features that inject JavaScript or HTML overlays are turned off. You want a pure TCP proxy for RDP. Any attempt by Cloudflare to "render" a page will destroy the connection.
**Pitfalls That Added Latency:**
* **Using WARP for Endpoints:** While elegant, requiring the corporate WARP client on user devices added a variable 15-50ms of latency depending on local network conditions. For a fixed, known set of finance workstations, distributing machine-specific service tokens for `cloudflared` access proved faster.
* **Complex Identity Providers:** Configuring Okta with strict per-request policies added ~200ms on the initial auth. We mitigated this by using a long `session_duration` and a one-time per-session MFA challenge. Ping is faster than Okta in our tests, but YMMV.
* **Not Using TCP Keep-Alives:** On the origin `cloudflared` side, ensure OS-level TCP keep-alive settings are aggressive. Idle RDP sessions timed out and reconnection through the Tunnel was slower than the VPN re-handshake.
**Bottom Line Numbers:**
The baseline VPN latency (from Frankfurt to London) was ~42ms. The initial, poorly configured Access setup added over 100ms. After implementing the Tunnel with SOCKS proxy, optimized session caching, and geo-routing, the added latency stabilized between **8ms and 15ms**. The total connection latency is now dominated by the physical distance, not the security layer.
Has anyone else pushed Access to its lowest latency limits for raw TCP protocols? I'm particularly interested if anyone has benchmarked the difference between a direct Tunnel connection and using Cloudflare's recently announced dedicated egress IPs for Tunnels in terms of jitter.
Show me the benchmarks
I'm a solutions architect at a mid-sized asset management firm, and we migrated our entire remote desktop infrastructure from a Cisco VPN to Cloudflare Zero Trust last year, specifically to support low-latency RDP for quants and analysts.
The most relevant points from my production rollout:
* **Actual Latency Add:** The tunnel method you found is correct. In our setup (analyst in NYC to host in our NJ datacenter), Access adds 8-12ms of consistent overhead. The traditional VPN gateway was adding a highly variable 25-80ms, which was the killer. The key is the tunnel keeps the entire path on Cloudflare's private backbone from their edge to your origin.
* **Session Persistence & Cost:** For a finance team that keeps connections open for hours, watch your concurrent session count. Cloudflare Access is billed per seat ($4/user/mo on the Zero Trust Starter plan), not by connection time or bandwidth, which made budgeting predictable for us. The 5GB/mo free tunnel bandwidth per account is easily exceeded by constant RDP traffic, so you'll need a paid plan.
* **Deployment Gotcha:** The biggest operational shift was moving from network-level rules to application-level policies. Each RDP host needs its own `cloudflared` daemon and tunnel, which is fine, but your Access policy must explicitly grant access to the specific user group and require a valid certificate from your IdP (we use Okta). It's not a "connect to the network" button anymore.
* **Where It Breaks:** It's fantastic for TCP-based protocols like RDP. If your team needs to also SMB file shares or use UDP-based applications from the same remote session, you'll hit a wall. This is an application proxy, not a network tunnel. We had to keep a slim VPN for a few legacy tools because of this.
My pick is the Cloudflare Zero Trust tunnel setup you outlined, specifically for the use case of dedicated RDP to known workstations. If your team also needs broad network access from the connected device or if you have a very large pool of rotating hosts (like a VDI cluster), tell us - those are the two constraints that might complicate it.