Lianja
Lianja
Multi-Hop SSH (SSH Through SSH)
See more SSH Examples
Demonstrates connecting to one SSH server through another: Application => ServerSSH1 => ServerSSH2. The ConnectThroughSsh method tunnels the second connection through the first. The technique chains further, so ServerSSH3 and beyond can be reached the same way.
Background: This is the "jump host" or bastion pattern: a gateway server is reachable from outside, and the machines you actually want are only reachable from inside. Each hop authenticates separately with its own credentials, and the result is an ordinary
Ssh object for the far server that happens to be routed through the near one. Any number of connections may be tunneled through a single existing connection, and closing an inner connection leaves the outer one alive for reuse.Chilkat Lianja Downloads
llSuccess = .F.
// This example requires the Chilkat API to have been previously unlocked.
// See Global Unlock Sample for sample code.
// Demonstrates connecting to one SSH server through another (SSH through SSH):
//
// Application => ServerSSH1 => ServerSSH2
//
// Any number of SSH connections may be tunneled through a single existing SSH connection, and
// the technique can be chained further to reach ServerSSH3, ServerSSH4, and so on.
loSsh1 = createobject("CkSsh")
// Connect directly to the 1st SSH server.
lcHostname = "jump.example.com"
lnPort = 22
llSuccess = loSsh1.Connect(lcHostname,lnPort)
if (llSuccess = .F.) then
? loSsh1.LastErrorText
release loSsh1
return
endif
// Normally you would not hard-code the password in source. You should instead obtain it
// from an interactive prompt, environment variable, or a secrets vault.
lcPassword = "mySshPassword"
llSuccess = loSsh1.AuthenticatePw("mySshLogin",lcPassword)
if (llSuccess = .F.) then
? loSsh1.LastErrorText
release loSsh1
return
endif
// Connect through the 1st SSH connection to reach the 2nd SSH server.
loSsh2 = createobject("CkSsh")
llSuccess = loSsh2.ConnectThroughSsh(loSsh1,"target.example.com",lnPort)
if (llSuccess = .F.) then
? loSsh2.LastErrorText
release loSsh1
release loSsh2
return
endif
// The 2nd server has its own credentials.
lcPassword2 = "mySshPassword2"
llSuccess = loSsh2.AuthenticatePw("mySshLogin2",lcPassword2)
if (llSuccess = .F.) then
? loSsh2.LastErrorText
release loSsh1
release loSsh2
return
endif
// ssh2 is now connected and authenticated, and can be used exactly as if it were connected
// directly. For example, open a session channel to run commands.
lnChannelNum = loSsh2.OpenSessionChannel()
if (lnChannelNum < 0) then
? loSsh2.LastErrorText
release loSsh1
release loSsh2
return
endif
// ... run commands on ssh2 ...
// Closing ssh2 closes the tunnel through ssh1. The ssh1 connection remains alive and may be
// reused for more connections.
loSsh2.Disconnect()
loSsh1.Disconnect()
release loSsh1
release loSsh2