Golang中client.Create("test.txt")报错SSH_FX_OP_UNSUPPORTED的解决方法

Golang中client.Create(“test.txt”)报错SSH_FX_OP_UNSUPPORTED的解决方法 我正在尝试将文件发送到SFTP服务器。我的理解是,我首先需要建立连接,然后创建一个“客户端”。对吗?

但是当我尝试执行 client.Create(filename) 时,出现了以下错误:

sftp: “FeatureNotSupported: This feature is not supported.” (SSH_FX_OP_UNSUPPORTED)

有人知道是什么原因导致这个错误吗?

package main

import (
	"fmt"
	"github.com/pkg/sftp"
	"golang.org/x/crypto/ssh"
	"io"
	"os"
	"strings"
)

func main() {
	send2ftp("./test.txt")
}

func send2ftp(filename string) {
	config := &ssh.ClientConfig{
		User: "username",
		Auth: []ssh.AuthMethod{
			ssh.Password("a_long_password"),
		},
		HostKeyCallback: ssh.InsecureIgnoreHostKey(),
	}

	conn, err := ssh.Dial("tcp", "sftp.test.com:22", config)
	if err != nil {
		if strings.Contains(err.Error(), "connection refused") {
			fmt.Println("SSH isn't up yet")
		} else {
			fmt.Println(err.Error())
		}
	}
	defer conn.Close()

	// create new SFTP client
	client, err := sftp.NewClient(conn)
	if err != nil {
		fmt.Println(err)
	}
	defer client.Close()

	// create destination file
	dstFile, err := client.Create(filename)
	if err != nil {
		fmt.Println(err)
	}
	defer dstFile.Close()

	// create source file
	srcFile, err := os.Open(filename)
	if err != nil {
		fmt.Println(err)
	}

	// copy source file to destination file
	io.Copy(dstFile, srcFile)
	if err != nil {
		fmt.Println(err)
	}
}

Play.golang


更多关于Golang中client.Create("test.txt")报错SSH_FX_OP_UNSUPPORTED的解决方法的实战教程也可以访问 https://www.itying.com/category-94-b0.html

2 回复

有什么线索知道是什么导致了这个问题吗?

经过数小时的研究,我找到了解决这个问题的办法(替换 client.Create):

// 创建目标文件
dstFile, err := client.OpenFile(filename, os.O_WRONLY|os.O_CREATE|os.O_TRUNC)
//dstFile, err := client.Create(filename)
if err != nil {
    fmt.Println(err)
}

更多关于Golang中client.Create("test.txt")报错SSH_FX_OP_UNSUPPORTED的解决方法的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


这个错误是因为SFTP服务器不支持Create操作。有些SFTP服务器实现可能只支持有限的操作集,或者需要特定的权限配置。

你可以尝试使用OpenFile方法替代Create,并指定适当的标志:

// 使用OpenFile替代Create,指定写入和创建标志
dstFile, err := client.OpenFile(filename, os.O_WRONLY|os.O_CREATE|os.O_TRUNC)
if err != nil {
    fmt.Println("OpenFile error:", err)
    return
}
defer dstFile.Close()

如果服务器仍然不支持,可以检查服务器是否支持其他写入方式。这里是一个更完整的示例,包含错误处理和备用方案:

func send2ftp(filename string) {
    // ... SSH连接代码保持不变 ...

    // 尝试多种方式创建/打开文件
    var dstFile *sftp.File
    var err error
    
    // 方法1: 尝试OpenFile
    dstFile, err = client.OpenFile(filename, os.O_WRONLY|os.O_CREATE|os.O_TRUNC)
    if err != nil {
        fmt.Println("OpenFile failed:", err)
        
        // 方法2: 检查文件是否存在,然后打开
        _, statErr := client.Stat(filename)
        if statErr == nil {
            // 文件存在,尝试以写入模式打开
            dstFile, err = client.OpenFile(filename, os.O_WRONLY|os.O_TRUNC)
            if err != nil {
                fmt.Println("Open existing file failed:", err)
                return
            }
        } else {
            // 文件不存在,服务器可能不支持创建操作
            fmt.Println("Server does not support file creation:", err)
            return
        }
    }
    defer dstFile.Close()

    // 打开源文件
    srcFile, err := os.Open(filename)
    if err != nil {
        fmt.Println("Open source file error:", err)
        return
    }
    defer srcFile.Close()

    // 复制文件内容
    _, err = io.Copy(dstFile, srcFile)
    if err != nil {
        fmt.Println("Copy error:", err)
        return
    }
    
    fmt.Println("File transferred successfully")
}

如果问题仍然存在,可能需要检查:

  1. 服务器端的SFTP配置和权限
  2. 用户是否有在目标目录创建文件的权限
  3. 服务器使用的SFTP协议版本

可以通过以下方式检查服务器能力:

// 检查服务器支持的扩展
extensions := client.Extensions()
fmt.Printf("Server extensions: %v\n", extensions)

// 检查服务器协议版本
fmt.Printf("Server protocol version: %d\n", client.SftpVersion())

某些SFTP服务器可能需要特定的配置才能支持文件创建操作。

回到顶部