hashicorp/terraform · error
Error creating new client connection via proxy: %s
Error message
Error creating new client connection via proxy: %s
What it means
Raised in BastionConnectFunc when ssh.NewClientConn(pConn, bAddr, bConf) fails after the HTTP proxy tunnel to the bastion was successfully established. The proxy CONNECT succeeded, but the SSH protocol handshake (key exchange, authentication) over that tunneled connection failed.
Source
Thrown at internal/communicator/ssh/communicator.go:852
// Wrap connection to bastion server if proxy server is configured
if p != nil {
var pConn net.Conn
var bConn ssh.Conn
var bChans <-chan ssh.NewChannel
var bReq <-chan *ssh.Request
RegisterDialerType()
pConn, err = newHttpProxyConn(p, bAddr)
if err != nil {
return nil, fmt.Errorf("Error connecting to proxy: %s", err)
}
bConn, bChans, bReq, err = ssh.NewClientConn(pConn, bAddr, bConf)
if err != nil {
return nil, fmt.Errorf("Error creating new client connection via proxy: %s", err)
}
bastion = ssh.NewClient(bConn, bChans, bReq)
} else {
bastion, err = ssh.Dial(bProto, bAddr, bConf)
}
if err != nil {
return nil, fmt.Errorf("Error connecting to bastion: %s", err)
}
log.Printf("[DEBUG] Connecting via bastion (%s) to host: %s", bAddr, addr)
conn, err := bastion.Dial(proto, addr)
if err != nil {
bastion.Close()
return nil, err
}
View on GitHub (pinned to c9def3e214)
Solutions
- Verify bastion_user, bastion_private_key, and bastion_password are correct for the bastion host.
- Confirm the bastion address and port (bAddr) the proxy is tunneling to is correct.
- Check the bastion sshd allows the key exchange algorithms supported by the Go SSH client.
- Test SSH to the bastion manually through the proxy to isolate the handshake failure.
Example fix
// before
connection {
bastion_host = var.bastion
proxy_host = var.proxy
}
// after
connection {
bastion_host = var.bastion
bastion_user = "ec2-user"
bastion_private_key = file("~/.ssh/bastion_key")
proxy_host = var.proxy
} Defensive patterns
Strategy: validation
Validate before calling
// Validate bastion SSH credentials through the proxy before the full run
func validateBastionViaProxy(proxyURL, bastionAddr, user, privateKey string) error {
// Use a quick SSH dial test through the proxy to catch auth/handshake issues early
signer, err := ssh.ParsePrivateKey([]byte(privateKey))
if err != nil {
return fmt.Errorf("invalid bastion private key: %w", err)
}
config := &ssh.ClientConfig{
User: user,
Auth: []ssh.AuthMethod{ssh.PublicKeys(signer)},
HostKeyCallback: ssh.InsecureIgnoreHostKey(),
Timeout: 10 * time.Second,
}
// (dial through proxy omitted for brevity)
_ = config
return nil
} Prevention
- Verify bastion_user and bastion_private_key match the bastion's authorized credentials.
- Confirm the bastion sshd supports the key exchange algorithms used by Go's SSH client.
- Test SSH to the bastion through the proxy manually before provisioning.
When it happens
Trigger: The proxy tunnel is open but the SSH handshake to the bastion fails: wrong bastion credentials, unsupported SSH key exchange algorithm, bastion sshd config mismatch, or the bastion private key is invalid for the tunneled connection.
Common situations: bastion_private_key does not match the bastion's authorized keys, bastion_user is wrong, the bastion sshd has restrictive algorithm/KexAlgorithms settings incompatible with the Go x/crypto/ssh client, or the proxy tunneled to the wrong port.
Related errors
- Error connecting to proxy: %s
- Error connecting to bastion: %s
- SSH authentication failed (%s@%s): %w
- Connection Error: StatusCode: %d
- failed to parse private key %q: %s
AI-assisted analysis of hashicorp/terraform@c9def3e214 (2026-08-07).
Data as JSON: /api/errors/46d5bb824458902d.
Report an issue: GitHub.