Skip to content

access tcp/ssh: service token ignored, browser auth attempted per-connection, TCP banner not delivered (2026.6.0 regression from 2026.5.1) #1673

@johnmcelroy-ai

Description

@johnmcelroy-ai

Summary

cloudflared access tcp (and access ssh) in 2026.6.0 ignores all headless auth credentials (service-token-id/secret flags, $TUNNEL_SERVICE_TOKEN_ID/SECRET env vars, -H header injection) and falls through to interactive browser auth on every new TCP connection. SSH banner never reaches the client; connection times out.

This is a regression from 2026.5.1, which honored service tokens correctly and never attempted browser auth when credentials were provided.

Environment

  • cloudflared client: 2026.6.0 (built 2026-06-08T18:16:09Z) on macOS arm64 (Apple Silicon)
  • cloudflared daemon: 2026.5.1 (remote tunnel daemon, working)
  • Tunnel mode: dashboard-managed (remote config), single hostname route <host>.example.com → ssh://localhost:2222
  • Access app: self-hosted, free tier, policy includes Emails + Service Auth

Steps to reproduce

  1. Create a CF Access Service Token + add to Access app policy as Include: Service Auth.
  2. Add hostname route in tunnel: <host>.example.com → ssh://localhost:2222.
  3. On client (where 2026.6.0 is running):
    export TUNNEL_SERVICE_TOKEN_ID="<id>.access"
    export TUNNEL_SERVICE_TOKEN_SECRET="<secret>"
    cloudflared access tcp \
      --hostname <host>.example.com \
      --url 127.0.0.1:2229 \
      --service-token-id "$TUNNEL_SERVICE_TOKEN_ID" \
      --service-token-secret "$TUNNEL_SERVICE_TOKEN_SECRET"
    
  4. From another shell: ssh -p 2229 user@127.0.0.1

Expected behavior (2026.5.1)

  • cloudflared authenticates against CF Access using the service token credentials
  • WebSocket established to CF edge, no browser prompt
  • TCP bytes (SSH banner, kex, payload) flow bidirectionally
  • SSH login succeeds

Actual behavior (2026.6.0)

  • cloudflared starts: INF Start Websocket listener host=127.0.0.1:2229 (looks fine)
  • On the first SSH connection attempt, cloudflared logs:
    A browser window should have opened at the following URL:
    https://<host>.example.com/cdn-cgi/access/cli?...
    
  • SSH client never receives a banner. Connection timed out during banner exchange.
  • Verified the service-token flag values DID reach cloudflared (--help shows them as defaults when env vars set).
  • Verified service token works for HTTP auth (curl -H "CF-Access-Client-Id:..." -H "CF-Access-Client-Secret:..." https://<host>.example.com/ returns HTTP 200 with a CF_Authorization cookie set).
  • Header injection via -H flag also attaches at WebSocket upgrade (cloudflared debug log shows Cf-Access-Client-Id + Cf-Access-Client-Secret headers in the WebSocket GET — and the WebSocket upgrades to HTTP 101 Switching Protocols), but per-connection auth still kicks off browser flow.
  • Cycle repeats on every TCP connection attempt.

Workaround

Downgrade to cloudflared 2026.5.1. No client-side workaround in 2026.6.0 has been found.

Repro environment context

  • macOS LaunchAgent (background process, cannot complete browser flow) calling cloudflared per-connection: broken.
  • Interactive foreground SSH: also broken (same per-connection retry on browser flow).
  • HTTP curl with service-token headers to same hostname: works (HTTP 200).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions