When you need to access Host C through an intermediate Host B where the private key resides, you're dealing with a classic SSH jump host scenario. This setup is common in secure environments where direct access to production servers is restricted.
The modern approach uses the ProxyJump directive in your SSH config file. Here's how to set it up:
Host HostB
HostName b.example.com
User bridgeuser
IdentityFile ~/.ssh/your_local_key
Host HostC
HostName c.example.com
User targetuser
ProxyJump HostB
ForwardAgent yes
If ProxyJump isn't available (OpenSSH < 7.3), you can use agent forwarding:
ssh -A -t user@HostB ssh user@HostC
Important: Only use this with trusted jump hosts as it exposes your local keys to the intermediate server.
For cases where you can't move the private key from Host B to your local machine:
ssh -J userB@HostB:port userC@HostC
Or with config:
Host HostC-via-B
HostName HostC
User userC
ProxyCommand ssh -W %h:%p userB@HostB
Add these flags for troubleshooting:
ssh -vvv -J user@HostB user@HostC
Common pitfalls:
- Ensure HostB can reach HostC
- Verify the private key on HostB has proper permissions (600)
- Check that AgentForwarding is enabled on HostB's sshd_config
Here's a complete working example for accessing a PostgreSQL server:
Host production-db-bastion
HostName bastion.example.com
User devops
IdentityFile ~/.ssh/devops_key
Host production-db
HostName db.internal.example.com
User postgres
ProxyJump production-db-bastion
LocalForward 5432 localhost:5432
Usage: ssh production-db
will tunnel through the bastion host and forward port 5432 locally.
When you need to SSH from machine A through intermediary B to target C, but the private key resides exclusively on B, traditional SSH forwarding won't work. This is particularly common in enterprise environments where security policies prevent key distribution.
Here's how to configure ~/.ssh/config
for this scenario:
Host intermediate-b HostName b.example.com User proxyuser IdentityFile ~/.ssh/id_rsa_local_to_b Host target-c-via-b HostName c.internal User targetuser ProxyCommand ssh -W %h:%p intermediate-b IdentityFile /home/proxyuser/.ssh/id_rsa_b_to_c
For more control, execute sequential SSH commands:
ssh -t b.example.com "ssh -i ~/.ssh/id_rsa_b_to_c targetuser@c.internal"
- Ensure
ssh-agent
forwarding isn't used (security risk) - Verify B has network access to C
- The private key on B should have 600 permissions
If connection fails, debug with:
ssh -vvv intermediate-b
Then verify the proxy can reach C:
ssh intermediate-b "nc -zv c.internal 22"