Golang:ssh运行远程脚本:没有这样的文件或目录

huangapple go评论116阅读模式
英文:

Golang: ssh running remote scripts: No such file or directory

问题

我正在使用ssh模块在远程机器上运行shell脚本:

// ssh-run.go
package main
import (
"bytes"
"flag"
"fmt"
"log"
"time"

"golang.org/x/crypto/ssh"

)

var (
flagUser = flag.String("user", "", "")
flagPwd = flag.String("pwd", "", "")
flagHost = flag.String("host", "", "")
flagCmd = flag.String("cmd", "", "")
)

func main() {
flag.Parse()
log.SetFlags(log.Lshortfile | log.LstdFlags)

cfg := ssh.ClientConfig {
    User: *flagUser,
    Auth: []ssh.AuthMethod(ssh.Password(*flagPwd)),
}

// skip err checking for short code
conn, _ := ssh.Dial("tcp", fmt.Sprintf("%s:22", *flagHost), &cfg)
defer conn.Close()
ss, _ := conn.NewSession()
defer ss.Close()

var out bytes.Buffer
ss.Stdout = &out
ss.Stderr = &out
ss.Run(*flagCmd)
fmt.Printf("err: %v, out: %v\n", err, out.String())

}

在远程Centos服务器上(运行了sshd),我将一个简单的Ping脚本放在主目录下,并运行了示例:

go run ssh-run.go -cmd "/bin/bash /home/me/try_ping.sh" -host 172.17.0.2 -pwd 123456 -user me

我得到了错误:

err: Process exited with status 127, out: /bin/bash: /home/me/try_ping.sh: No such file or directory

但是当远程服务器是Ubuntu服务器时,Ping脚本可以正常工作。

在面对远程脚本运行时,Centos和Ubuntu之间有什么区别?我需要在许多类UNIX操作系统下运行远程脚本,如何解决它们之间的差异?

英文:

I'm using ssh module to run shell scripts on remote machine:

// ssh-run.go
package main
import (
    "bytes"
    "flag"
    "fmt"
    "log"
    "time"
    
    "golang.org/x/crypto/ssh"
)

var (
    flagUser = flag.String("user", "", "")
    flagPwd = flag.String("pwd", "", "")
    flagHost = flag.String("host", "", "")
    flagCmd = flag.String("cmd", "", "")
)

func main() {
    flag.Parse()
    log.SetFlags(log.Lshortfile | log.LstdFlags)

    cfg := ssh.ClientConfig {
        User: *flagUser,
        Auth: []ssh.AuthMethod(ssh.Password(*flagPwd)),
    }
    
    // skip err checking for short code
    conn, _ := ssh.Dial("tcp", fmt.Sprintf("%s:22", *flagHost), &cfg)
    defer conn.Close()
    ss, _ := conn.NewSession()
    defer ss.Close()

    var out bytes.Buffer
    ss.Stdout = &out
    ss.Stderr = &out
    ss.Run(*flagCmd)
    fmt.Printf("err: %v, out: %v\n", err, out.String())
}

On a remote Centos server(sshd is running), I put a simple Ping script under home path, and I run the demo:

go run ssh-run.go -cmd "/bin/bash /home/me/try_ping.sh" -host 172.17.0.2 -pwd 123456 -user me

I got the error:

err: Process exited with status 127, out: /bin/bash: /home/me/try_ping.sh: No such file or directory

But when the remote server is a Ubuntu server, the Ping script works well.

What is the difference between Centos and Ubuntu when facing remote script running? I need to run remote scripts under many UNIX-like OS, How to fix the gap between them?

答案1

得分: 1

我明白了。通常情况下,当我们需要通过SSH将一个长命令传递给远程服务器时,比如 sh /path/to/script.sh,我们可以通过以下方式运行它(单引号也可以使用):

ssh user@1.2.3.4 "sh /path/to/script.sh"

在这里,我们使用双引号来禁用shell参数分割。

然而,在我的真实的golang代码中(上面的代码是从我的项目中截取的,并使用flags进行测试),我也使用了双引号,而且golang的SSH包也会将这两个双引号发送到远程SSH服务器,然后远程SSH不知道如何定位以双引号为前缀的文件。

令人烦恼的是,错误消息没有带上双引号,让我对双引号感到困惑。

谢谢 @JimB Golang:ssh运行远程脚本:没有这样的文件或目录

英文:

I go the reason. Normally, when we need to pass a long command to remote server via SSH, say sh /path/to/script.sh, we can run it via(single quote also works):

ssh user@1.2.3.4 "sh /path/to/script.sh"

here, we use double quote to disable shell parameter split.

While in my true golang code (above code is cut from my project and use flags for testing.), I also used double quote, and the golang SSH package also send the tow double quote to remote SSH server, then remote SSH don't know how to locate files prefixed with double quote.

The annoy things is that, the error message do not carry the double quote, blind me about the double quote.

Thanks @JimB Golang:ssh运行远程脚本:没有这样的文件或目录

huangapple
  • 本文由 发表于 2016年12月2日 16:17:38
  • 转载请务必保留本文链接:https://go.coder-hub.com/40927577.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定