2

求助,关于 http body 的传输

 2 years ago
source link: https://www.v2ex.com/t/875234
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

V2EX  ›  Go 编程语言

求助,关于 http body 的传输

  hzjseasea · 1 小时 53 分钟前 · 553 次点击

有一个场景是要把前一个请求 get 到的 body 原模原样的拿下来作为另外一个 post 请求的请求体,然后我就有一个疑问,对于小体积的 body 来说无所谓,哪怕是直接将 body copy 一份都没事,但是对于大体积的 body 来说,如果直接用第一种方式 copy 一份的话,那整个内容都会保存在内存里,高并发的环境下对于内存小的机器会不会直接撑爆了,然后我就想了下面两种方式,第二种用函数返回的方式我觉得也是存在内存里面的,用 pipe 的方式更像是流式的方式传输? 望指教

// 直接 copy 一份
func GetBody() ([]byte, error) {
	resp, err := http.Get("http://www.baidu.com")
	if err != nil {
		return nil, err
	}
	defer resp.Body.Close()
	body, _ := ioutil.ReadAll(resp.Body)
	return body, nil
}

func main() {
	body, _ := GetBody()
	// ... deal with body
	fmt.Println(body)

}
// 直接将 response body 抛出来
func GetBody() (io.ReadCloser, error) {
	resp, err := http.Get("http://www.baidu.com")
	if err != nil {
		return nil, err
	}
	return resp.Body, nil
}

func main() {
	body, err := GetBody()
	if err != nil {
		fmt.Println(err)
	}
	defer body.Close()

	// ... deal with body

}

// 通过 io.pipe 的方式传输
func PipeBody(w *io.PipeWriter) {
	resp, err := http.Get("http://www.baidu.com")
	if err != nil {
		log.Println(err)
	}
	defer resp.Body.Close()
	io.Copy(w, resp.Body)
}

func main() {
	reader, writer := io.Pipe()
	go func() {
		defer writer.Close()
		PipeBody(writer)
	}()

	// ... deal with body, for example
	body, _ := ioutil.ReadAll(reader)
	fmt.Println(string(body))
}

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK