2015-09-22 6 views
13

は、それがサーバーの場合空のリクエストBodyを確認する最も良い方法は何ですか? <a href="https://golang.org/src/net/http/request.go" rel="noreferrer">documentation</a>から

がリクエストボディを要求し、常に非nilのですが、全く体が存在しない場合、直ちにEOFを返すことを述べています。

はん。ContentLengthの場合、ドキュメントはボディがnilでない場合は0の値は、不明を意味し、クライアントの要求について

を述べています。

だから、あなたは常に内容が何であるかを知るために身体を読み取る必要があるん。ContentLength

r *http.Request 
if r.ContentLength == 0 { 
    //empty body 
} 

またはEOF

type Input struct { 
    Name *string `json:"name"` 
} 

input := new(Input) 

if err := json.NewDecoder(r.Body).Decode(input); err.Error() == "EOF" { 
//empty body 
} 
+2

明らかにEOF、 'コンテンツLength'は、クライアントがまたはに設定することはできませんヘッダーです。 – thwd

+0

エラーの文字列値に悩まされないでください。 'io.EOF'を探しているなら' if err == io.EOF'を実行してください。文字列の表示を見ても、信じられないほど壊れやすい。 –

答えて

15

をチェックするためにチェックすることをお勧めします。クライアントはContent-Lengthのチャンクエンコーディングでボディを送信することもできますし、エラーが発生してContent-Lengthという本文を送信することさえできます。クライアントは、それが送信しようとしていることを送信する義務は決してありません。

EOFチェックは、空のボディのみをチェックしている場合に機能しますが、EOF文字列以外のエラーケースもチェックします。

err := json.NewDecoder(r.Body).Decode(input) 
switch { 
case err == io.EOF: 
    // empty body 
case err != nil: 
    // other error 
} 

あなたはまた、非整列化する前に体全体を読むことができます:

body, err := ioutil.ReadAll(r.Body) 

か、あまりにも多くのデータ

body, err := ioutil.ReadAll(io.LimitReader(r.Body, readLimit)) 
0

心配している場合は通常、あなたが方法を見ることができますが身体を予期するかどうかを知る要求。

例えば、GETリクエストはボディを持つべきではなく、PUTリクエストとPOSTリクエストにボディが必要です。

だからあなたif主張もそのように書くことができます。

if r.Method == "PUT" || r.Method == "POST" { 
    // do something that depends on the body content 
} else { 
    // don't even try to read the body and do something else 
} 
関連する問題