Estoy usando go-scp e intento copiar al servidor solarwinds (servidor de Windows) y obtengo un error de tiempo de espera agotado mientras que probé la línea de comando scp, funciona bien.
También descubrí que después de eliminar la opción -q en la línea err := a.Session.Run(fmt.Sprintf("%s -qt %q", a.RemoteBinary, remotePat) en la función CopyPassThru en la biblioteca go-scp, hay no hubo un error de tiempo de espera agotado, pero el archivo estaba vacío en el servidor remoto
No puedo usar SSH en el servidor solarwinds a través de la línea de comandos.
Código cortado como se muestra a continuación
package main import ( "fmt" scp "github.com/bramvdbogaerde/go-scp" "golang.org/x/crypto/ssh" "os" "strings" "time" ) func main() { // Use SSH key authentication from the auth package // we ignore the host key in this example, please change this if you use this library // create ssh client config var authParam ssh.AuthMethod authParam = ssh.Password("1234") clientConfig := &ssh.ClientConfig{ User: "admin", Auth: []ssh.AuthMethod{ authParam, }, HostKeyCallback: ssh.InsecureIgnoreHostKey(), Timeout:time.Minute, } // For other authentication methods see ssh.ClientConfig and ssh.AuthMethod // Create a new SCP client client := scp.NewClient("10.154.92.32:22", clientConfig) // Connect to the remote server err := client.Connect() if err != nil { fmt.Println("Couldn't establish a connection to the remote server ", err) return } // Close client connection after the file has been copied defer client.Close() // Finally, copy the file over // Usage: CopyFile(fileReader, remotePath, permission) fileString := "testing \n" myReader := strings.NewReader(fileString) err = client.CopyFile(myReader, "/test", "0777") if err != nil { fmt.Println("Error while copying file ", err) } }Para cualquiera que tenga problemas con ese paquete scp (yo también tuve problemas), esta es una solución alternativa que usa cat para transferir archivos individuales. Utiliza solo el paquete ssh .
La idea es usar cat sin argumentos para leer desde la entrada estándar. En nuestro objeto de sesión proporcionamos nuestro archivo local como entrada estándar. Luego canalizamos la salida de cat con > al archivo deseado.
La forma inversa es similar, esta vez interceptamos la salida estándar de nuestro objeto de sesión. Cateamos el archivo remoto y copiamos la salida estándar de la sesión a nuestro archivo local.
Aquí está el código:
package main import ( "bytes" "errors" "os" "golang.org/x/crypto/ssh" ) func main() { config := &ssh.ClientConfig{ HostKeyCallback: ssh.InsecureIgnoreHostKey(), User: "user", Auth: []ssh.AuthMethod{ssh.Password("password")}, } client, err := ssh.Dial("tcp", "10.0.0.1:22", config) if err != nil { panic(err) } defer client.Close() err = setFile(client, "local/file", "remote/file") if err != nil { panic(err) } err = getFile(client, "remote/file", "local/file") if err != nil { panic(err) } } func setFile(client *ssh.Client, from, to string) error { f, err := os.Open(from) if err != nil { return err } defer f.Close() session, err := client.NewSession() if err != nil { return err } defer session.Close() session.Stdin = f var stderr bytes.Buffer session.Stderr = &stderr err = session.Run("cat > '" + to + "'") if err != nil && stderr.Len() > 0 { err = errors.New(err.Error() + ": " + string(stderr.Bytes())) } return err } func getFile(client *ssh.Client, from, to string) error { f, err := os.Create(to) if err != nil { return err } defer f.Close() session, err := client.NewSession() if err != nil { return err } defer session.Close() session.Stdout = f var stderr bytes.Buffer session.Stderr = &stderr err = session.Run("cat '" + from + "'") if err != nil && stderr.Len() > 0 { err = errors.New(err.Error() + ": " + string(stderr.Bytes())) } return err }