Golang中可以使用 golang.org/x/crypto/ssh 包作为SSH客户端或者SSH服务使用。这篇文章将简单记录下作为客户端使用的一些内容。
基础说明Package ssh implements an SSH client and server.
作为客户端与SSH服务器操作上来说主要分为三步:
ClientClientSessionSession
使用演示
单次通讯
SessionRunOutputCombinedOutput
package mainimport ("bytes""fmt""log""golang.org/x/crypto/ssh"
)func main() {// 设置客户端请求参数// var hostKey ssh.PublicKeyconfig := &ssh.ClientConfig{User: "root",Auth: []ssh.AuthMethod{ssh.Password("naisu233"),},// HostKeyCallback: ssh.FixedHostKey(hostKey),HostKeyCallback: ssh.InsecureIgnoreHostKey(), // 忽略主机密钥}// 作为客户端连接SSH服务器client, err := ssh.Dial("tcp", "192.168.31.142:22", config)if err != nil {log.Fatal("Failed to dial: ", err)}defer client.Close()// 创建会话session, err := client.NewSession()if err != nil {log.Fatal("Failed to create session: ", err)}defer session.Close()// 设置会话标准输出,运行命令var b bytes.Buffersession.Stdout = &bif err := session.Run("cat /proc/cpuinfo"); err != nil {log.Fatal("Failed to run: " + err.Error())}fmt.Println(b.String())
}
Sessiontop
连续通讯(远程终端)
SessionStartShellWaitShell
package mainimport ("log""os""golang.org/x/crypto/ssh""golang.org/x/term"
)func main() {// 设置客户端请求参数// var hostKey ssh.PublicKeyconfig := &ssh.ClientConfig{User: "root",Auth: []ssh.AuthMethod{ssh.Password("naisu233"),},// HostKeyCallback: ssh.FixedHostKey(hostKey),HostKeyCallback: ssh.InsecureIgnoreHostKey(), // 忽略主机密钥}// 作为客户端连接SSH服务器conn, err := ssh.Dial("tcp", "192.168.31.142:22", config)if err != nil {log.Fatal("unable to connect: ", err)}defer conn.Close()// 创建会话session, err := conn.NewSession()if err != nil {log.Fatal("unable to create session: ", err)}defer session.Close()// 设置会话的标准输出、错误输出、标准输入session.Stdout = os.Stdoutsession.Stderr = os.Stderrsession.Stdin = os.Stdin// 设置终端参数modes := ssh.TerminalModes{ssh.ECHO: 0, // disable echoingssh.TTY_OP_ISPEED: 14400, // input speed = 14.4kbaudssh.TTY_OP_OSPEED: 14400, // output speed = 14.4kbaud}termWidth, termHeight, err := term.GetSize(int(os.Stdout.Fd())) // 获取当前标准输出终端窗口尺寸 // 该操作可能有的平台上不可用,那么下面手动指定终端尺寸即可if err != nil {log.Fatal("unable to terminal.GetSize: ", err)}// 设置虚拟终端与远程会话关联if err := session.RequestPty("xterm", termHeight, termWidth, modes); err != nil {log.Fatal("request for pseudo terminal failed: ", err)}// 启动远程Shellif err := session.Shell(); err != nil {log.Fatal("failed to start shell: ", err)}// 阻塞直至结束会话if err := session.Wait(); err != nil {log.Fatal("exit error: ", err)}
}
总结
Golang作为客户端与SSH服务器交互还是比较方便的,实际使用中更多的需要注意阻塞方法以及持续执行的外部程序的处理。