diff --git a/binding/json.go b/binding/json.go index e928a8c1..fea17bb2 100644 --- a/binding/json.go +++ b/binding/json.go @@ -5,6 +5,8 @@ package binding import ( + "bytes" + "io" "net/http" "github.com/gin-gonic/gin/json" @@ -22,7 +24,15 @@ func (jsonBinding) Name() string { } func (jsonBinding) Bind(req *http.Request, obj interface{}) error { - decoder := json.NewDecoder(req.Body) + return decodeJSON(req.Body, obj) +} + +func (jsonBinding) BindBody(body []byte, obj interface{}) error { + return decodeJSON(bytes.NewReader(body), obj) +} + +func decodeJSON(r io.Reader, obj interface{}) error { + decoder := json.NewDecoder(r) if EnableDecoderUseNumber { decoder.UseNumber() } diff --git a/binding/msgpack.go b/binding/msgpack.go index 7faea4b5..b7f73197 100644 --- a/binding/msgpack.go +++ b/binding/msgpack.go @@ -5,6 +5,8 @@ package binding import ( + "bytes" + "io" "net/http" "github.com/ugorji/go/codec" @@ -17,7 +19,16 @@ func (msgpackBinding) Name() string { } func (msgpackBinding) Bind(req *http.Request, obj interface{}) error { - if err := codec.NewDecoder(req.Body, new(codec.MsgpackHandle)).Decode(&obj); err != nil { + return decodeMsgPack(req.Body, obj) +} + +func (msgpackBinding) BindBody(body []byte, obj interface{}) error { + return decodeMsgPack(bytes.NewReader(body), obj) +} + +func decodeMsgPack(r io.Reader, obj interface{}) error { + cdc := new(codec.MsgpackHandle) + if err := codec.NewDecoder(r, cdc).Decode(&obj); err != nil { return err } return validate(obj) diff --git a/binding/protobuf.go b/binding/protobuf.go index c7eb84e9..540e9c1f 100644 --- a/binding/protobuf.go +++ b/binding/protobuf.go @@ -17,19 +17,20 @@ func (protobufBinding) Name() string { return "protobuf" } -func (protobufBinding) Bind(req *http.Request, obj interface{}) error { - +func (b protobufBinding) Bind(req *http.Request, obj interface{}) error { buf, err := ioutil.ReadAll(req.Body) if err != nil { return err } + return b.BindBody(buf, obj) +} - if err = proto.Unmarshal(buf, obj.(proto.Message)); err != nil { +func (protobufBinding) BindBody(body []byte, obj interface{}) error { + if err := proto.Unmarshal(body, obj.(proto.Message)); err != nil { return err } - - //Here it's same to return validate(obj), but util now we cann't add `binding:""` to the struct - //which automatically generate by gen-proto + // Here it's same to return validate(obj), but util now we cann't add + // `binding:""` to the struct which automatically generate by gen-proto return nil - //return validate(obj) + // return validate(obj) } diff --git a/binding/xml.go b/binding/xml.go index f84a6b7f..4e901149 100644 --- a/binding/xml.go +++ b/binding/xml.go @@ -5,7 +5,9 @@ package binding import ( + "bytes" "encoding/xml" + "io" "net/http" ) @@ -16,7 +18,14 @@ func (xmlBinding) Name() string { } func (xmlBinding) Bind(req *http.Request, obj interface{}) error { - decoder := xml.NewDecoder(req.Body) + return decodeXML(req.Body, obj) +} + +func (xmlBinding) BindBody(body []byte, obj interface{}) error { + return decodeXML(bytes.NewReader(body), obj) +} +func decodeXML(r io.Reader, obj interface{}) error { + decoder := xml.NewDecoder(r) if err := decoder.Decode(obj); err != nil { return err }