为了账号安全,请及时绑定邮箱和手机立即绑定

多部分编写器创建表单文件卡住

多部分编写器创建表单文件卡住

Go
慕勒3428872 2022-09-05 10:24:28
尝试使用 go 发布多部分/表单数据图像图像文件从请求客户端接收,并且已另存为多部分。文件这是我的代码func postImage(file multipart.File, url string, filename string) (*http.Response, error) {    r, w := io.Pipe()    defer w.Close()    m := multipart.NewWriter(w)    defer m.Close()    errchan := make(chan error)    defer close(errchan)    go func() {        part, err := m.CreateFormFile("file", filename)        log.Println(err)        if err != nil {            errchan <- err            return        }        if _, err := io.Copy(part, file); err != nil {            errchan <- err            return        }    }()    merr := <-errchan    if merr != nil {        return nil, merr    }    resp, err := http.Post(url, m.FormDataContentType(), r)    if err != nil {        return nil, err    }    defer resp.Body.Close()    return resp, err}当我尝试使用它时,它卡在永远不会返回任何东西part, err := m.CreateFormFile("file", filename)任何解决方案?
查看完整描述

1 回答

?
湖上湖

TA贡献2003条经验 获得超2个赞

使用管道错误将错误传播回主 goroutine。关闭管道的写入端,以防止客户端在读取时永久阻塞。关闭管道的读取侧,以确保 goroutine 退出。


func postImage(file multipart.File, url string, filename string) (*http.Response, error) {

    r, w := io.Pipe()


    // Close the read side of the pipe to ensure that

    // the goroutine exits in the case where http.Post

    // does not read all of the request body.

    defer r.Close()


    m := multipart.NewWriter(w)


    go func() {

        part, err := m.CreateFormFile("file", filename)

        if err != nil {

            // The error is returned from read on the pipe.

            w.CloseWithError(err)

            return

        }

        if _, err := io.Copy(part, file); err != nil {

            // The error is returned from read on the pipe.

            w.CloseWithError(err)

            return

        }

        // The http.Post function reads the pipe until 

        // an error or EOF. Close to return an EOF to

        // http.Post.

        w.Close()

    }()


    resp, err := http.Post(url, m.FormDataContentType(), r)

    if err != nil {

        return nil, err

    }

    defer resp.Body.Close()


    return resp, err

}


查看完整回答
反对 回复 2022-09-05
  • 1 回答
  • 0 关注
  • 59 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信