title: 【転載】golang の http.request.body の再利用
date: 2021-07-06 11:14:22
comment: false
toc: true
category:
- Golang
tags: - 転載
- Go
- golang
- 再利用
- http
- request
- body
この記事は転載です:golang の http.request.body の再利用 - Go 言語中文網 - Golang 中文コミュニティ
問題とシナリオ#
ビジネスの中で http.request.body を配信する必要があるシナリオがあります。例えば、WeChat のコールバックメッセージは一つのアドレスしか指定できないため、他のサービスにメッセージをコピーして送信したいと考えています。サービス B と WeChat のコールバックを受信するサービス A が一緒に WeChat のコールバック情報を処理します。
解決策#
最初に考えたのは http.request を直接転送することでした。ReverseProxyを使用して、サービス A からサービス B に http.request を直接転送します。しかし、WeChat には認証などの問題が関わっているため、完全に調整するのは非常に面倒です。そこで考え方を変え、http.request.body の内容を直接サービス B にポストすることにしました。
しかし、http.request は readcloser です。http.request を readAll する際に、http.request の中の情報を再度読み取ることができません。
どうすれば http.request.body をコピーして使用できるのでしょうか?#
ここで c は http のコンテキストを示します
// requestの内容を読み取る
var bodyBytes []byte
if c.Request.Body != nil {
bodyBytes, _ = ioutil.ReadAll(c.Request.Body)
}
// 読み取った内容を再度書き込む
c.Request.Body = ioutil.NopCloser(bytes.NewBuffer(bodyBytes))
1. まず、body を http.request から読み取り、変数に保存します。
2. 次に、変数のデータを ioutil.NopCloser メソッドを使用して http.request に書き戻します。
https://golang.org/pkg/io/ioutil/#NopCloser
NopCloser は、提供された Reader r をラップする無操作の Close メソッドを持つ ReadCloser を返します。
NopCloser は無操作の Close メソッドで Reader r をラップした ReadCloser インターフェースを返します。
これで再度 c.request を使用して処理することができます。