Azure / Azure/azure-cli-extensions
az network bastion ssh/tunnel fails with "Invalid WebSocket Header" on Azure CLI 2.76+ (Python 3.13 builds) on Windows
- Dominant language
- Python
- Stars
- 454
- Forks
- 1.7k
- Avg merge
- 2d 19h
- Merged PRs (30d)
- 64
Description
### Describe the bug
az network bastion ssh, az network bastion tunnel, and any other bastion extension command that establishes a WebSocket tunnel fails immediately with Exception in handling client: Invalid WebSocket Header on Windows installations of Azure CLI 2.76 and later.
The HTTP POST to /api/tokens on the Bastion host succeeds (returns 200), but the subsequent WebSocket upgrade handshake is rejected internally. The tunnel terminates before any data can be forwarded. az network bastion rdp (which downloads an .rdp file without using WebSocket tunneling) works correctly, confirming the issue is specific to the tunnel code path.
**To reproduce:**
On a Windows 11 machine with Azure CLI installed via MSI (2.76.0 through 2.85.0 — any version bundling Python 3.13):
### Related command
az network bastion ssh --name "" --resource-group "" --target-resource-id "" --auth-type "AAD" --debug
_Also happens with "ssh-key" authorization type_
### Errors
cli.azext_bastion.tunnel: Exception in handling client: Invalid WebSocket Header
cli.azext_bastion.tunnel: Cleaning up session
### Issue script & Debug output
urllib3.connectionpool: https://bst-.bastion.azure.com:443 "POST /api/tokens HTTP/1.1" 200 None
cli.azext_bastion.tunnel: Exception in handling client: Invalid WebSocket Header
cli.azext_bastion.tunnel: Cleaning up session
urllib3.connectionpool: https://bst-.bastion.azure.com:443 "DELETE /api/tokens/ HTTP/1.1" 204 0
### Expected behavior
The SSH session should open through the Bastion tunnel.
### Environment Summary
OS: Windows 11 (26200)
Azure CLI: 2.76.0, 2.84.0, 2.85.0 (MSI install) — all fail
Python (bundled): 3.13.x
bastion extension: 1.3.0, 1.4.0, 1.4.1, 1.4.2, 1.4.3 — all fail
ssh extension: 2.0.7
az version
{
"azure-cli": "2.85.0",
"azure-cli-core": "2.85.0",
"azure-cli-telemetry": "1.1.0",
"extensions": {
"bastion": "1.4.3",
"ssh": "2.0.7"
}
}
### Additional context
This a Linux VM running Ubuntu 24.04 pro. I have tried this on multiple computers and getting the same error. Oddly, the ability to ssh into the vm from my local terminal was working for me the first few days after I first setup this VM. After another user started accessing the VM is when it seems like it stopped working. I have also tried with another bastion instance on a Windows VM that we have in a different subscription, and I am getting the same error there as well (Invalid WebSocket Header), but I am still able to RDP into that Windows VM through my native client. I am also still able to access the Linux VM through Bastion in the Azure portal via ssh-key and Entra authorization.
Contributor guide
Research direction
Start by reproducing `az network bastion ssh` or `az network bastion tunnel` on Windows with Azure CLI 2.76+ and `--debug`, then inspect the Bastion extension's WebSocket tunnel path after the successful `/api/tokens` POST. Compare the failing handshake with the working non-WebSocket `az network bastion rdp` path. Done means SSH and tunnel sessions open and forward data without `Invalid WebSocket Header`.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- azure, python
- Domain
- cli, cloud, networking
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 48/100