【问题标题】:Program fails with: write tcp broken pipe error程序失败:write tcp broken pipe error
【发布时间】:2021-08-24 21:22:53
【问题描述】:

我有一个使用 github.com/jlaffaye/ftp 下载文件的 go 应用程序,这是一个实现文件传输协议 (FTP) 的库

定义了一个带有 FTP 连接的结构

type Client struct {
    conn *ftp.ServerConn
    sync.Mutex
}

我有一个全球客户

var cli *Client = nil

然后我将其初始化并分配给全局变量以供以后使用

    conn, err := ftp.Dial(cfg.Host+cfg.Port, ftp.DialWithContext(ctx))
    if err != nil {
        return fmt.Errorf("ftp dial error: %v", err)
    }

    err = conn.Login(cfg.Username, pwd)
    if err != nil {
        return fmt.Errorf("ftp login error: %v", err)
    }

    c := &Client{}

    c.Lock()
    c.conn = conn
    cli = c
    c.Unlock()

我有一个 http 处理程序,它从 Client 结构中获取 conn 字段并调用

    fileNames, err := conn.NameList(".")
    if err != nil {
        return err
    }

大多数情况下,应用程序在调用 conn.NameList(".") 时失败并出现错误

write tcp xxx.xxx.xx.x:48572-\u003exx.xxx.xxx.xxx:21: write: broken pipe

有时

write tcp xxx.xxx.xx.xx:63037-\u003exx.xxx.xxx.xxx:21: wsasend: An established connection was aborted by the software in your host machine

我不会过早关闭连接。 有谁知道为什么会这样?或者您可以推荐一个更好的使用 FTP 的库?

根据问题是否同时运行多个服务,以及它是否安全。

当一个进程正在运行时,另一个进程直到setIsRunning(false) is called才能运行

func (s *Service) setIsRunning(b bool) error {
    mu := &sync.Mutex{}
    mu.Lock()
    defer mu.Unlock()

    if b && s.isRunning {
        return errors.New("already running")
    }
    s.isRunning = b

    return nil
}

在其运行时尝试调用该处理程序将产生 "error":"already running"

我在从全局Client 读取时也使用互斥锁

    cli.Lock()
    conn = cli.conn
    cli.Unlock()

【问题讨论】:

  • 是否有多个请求使用该连接提供服务?该连接是线程安全的吗?
  • @BurakSerdar,一次只运行一个请求,而且我在使用全局 Client 时有互斥锁
  • @BurakSerdar 在问题描述中添加了对您的问题的更多说明
  • setIsRunning 是错误的。您的互斥锁是本地的,它没有保护任何东西。将互斥锁放入s
  • @BurakSerdar 似乎切换到非全局客户端可以解决问题。我有方法接收器类型为cli *Client 这也是正确的,对吧?

标签: go ftp pipe


【解决方案1】:

切换到非全局客户端可以解决问题

【讨论】:

    猜你喜欢
    • 2017-02-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多