Skip to content

Commit

Permalink
Merge pull request #64 from guonaihong/setbody-bindbody-63-62
Browse files Browse the repository at this point in the history
SetBody支持io.Reader,BindBody支持io.Writer
  • Loading branch information
guonaihong authored Oct 8, 2019
2 parents efa04e1 + 597e2be commit 4501526
Show file tree
Hide file tree
Showing 6 changed files with 85 additions and 74 deletions.
26 changes: 20 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ gout 是go写的http 客户端,为提高工作效率而开发
- [http header](#http-header)
- [http body](#http-body)
- [body](#body)
- [SetBody](#setbody)
- [BindBody](#bindbody)
- [json](#json)
- [yaml](#yaml)
- [xml](#xml)
Expand Down Expand Up @@ -184,24 +186,36 @@ SetHeader([]string{"active", "enable", "action", "drop"})

## http body
### body
#### SetBody
* SetBody 设置string, []byte等类型数据到http body里面
* BindBody bind body到string, []byte等类型变量里面
```go
// 设置string变量至请求的http body
err := gout.New(nil).POST(url).SetBody("hello world"/*更多支持类型请看下面*/).Do()
err := gout.New(nil).POST(url).SetBody(/*支持的类型如下*/).Do()
// 设置实现io.Reader接口的变量至 请求的http body
err = gout.POST(url).SetBody(bytes.NewBufferString("hello world")).Code(&code).Do()
```
#### bindBody
* BindBody bind body到string, []byte等类型变量里面
```go
// 解析http body到string类型变量里面
var s string
err := gout.New(nil).GET(url).BindBody(&s/*支持的指针类型变量如下*/).Do()
err := gout.New(nil).GET(url).BindBody(&s/*更多支持指针类型变量请看下面*/).Do()
// 解析http body至实现io.Writer接口的变量里面
var b bytes.Buffer{}
err = gout.GET(url).BindBody(&b).Code(&code).Do()
```
## 支持的类型有
#### 支持的类型有
* io.Reader(SetBody 支持)
* io.Writer(BindBody 支持)
* int, int8, int16, int32, int64
* uint, uint8, uint16, uint32, uint64
* string
* []byte
* float32, float64

## 明确不支持的类型有
#### 明确不支持的类型有
* struct
* array, slice

Expand Down
5 changes: 5 additions & 0 deletions decode/body.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,11 @@ func (b *BodyDecode) Decode(r io.Reader) error {
}

func DecodeBody(r io.Reader, obj interface{}) error {
if w, ok := obj.(io.Writer); ok {
_, err := io.Copy(w, r)
return err
}

all, err := ioutil.ReadAll(r)
if err != nil {
return err
Expand Down
3 changes: 3 additions & 0 deletions decode/body_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,9 @@ func testDecodeBody(t *testing.T, funcName string) {

{r: bytes.NewBufferString("test string"), need: core.NewPtrVal("test string"), got: new(string)},
{r: bytes.NewBuffer([]byte("test bytes")), need: core.NewPtrVal([]byte("test bytes")), got: new([]byte)},

// test io.Writer
{r: bytes.NewBuffer([]byte("test buffer")), need: bytes.NewBufferString("test buffer"), got: bytes.NewBufferString("")},
}

for _, v := range tests {
Expand Down
6 changes: 6 additions & 0 deletions encode/body.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,14 @@ func NewBodyEncode(obj interface{}) *BodyEncode {
}

func (b *BodyEncode) Encode(w io.Writer) error {
if r, ok := b.obj.(io.Reader); ok {
_, err := io.Copy(w, r)
return err
}

val := reflect.ValueOf(b.obj)
val = core.LoopElem(val)

switch t := val.Kind(); t {
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
Expand Down
12 changes: 11 additions & 1 deletion encode/body_test.go
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
package encode

import (
"bytes"
"github.com/guonaihong/gout/core"
"github.com/stretchr/testify/assert"
"strings"
"testing"
"time"
)

func TestNewBodyEncode(t *testing.T) {
Expand All @@ -18,6 +20,12 @@ type bodyTest struct {
need string
}

func Test_body_EncodeFail(t *testing.T) {
b := NewBodyEncode(&time.Time{})
err := b.Encode(bytes.NewBufferString("hello world"))
assert.Error(t, err)
}

func Test_body_Encode(t *testing.T) {

tests := []bodyTest{
Expand All @@ -35,8 +43,10 @@ func Test_body_Encode(t *testing.T) {
{w: &strings.Builder{}, set: []byte("test bytes"), need: "test bytes"},
{w: &strings.Builder{}, set: "test string", need: "test string"},
{w: &strings.Builder{}, set: int(1), need: "1"},

{w: &strings.Builder{}, set: core.NewPtrVal(1010), need: "1010"},

// test io.Reader
{w: &strings.Builder{}, set: bytes.NewBufferString("set body:hello world"), need: "set body:hello world"},
}

for _, v := range tests {
Expand Down
107 changes: 40 additions & 67 deletions group_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -616,12 +616,19 @@ type testBodyNeed struct {
Int64 bool `form:"int64"`
String bool `form:"string"`
Bytes bool `form:"bytes"`
Reader bool `form:"reader"`
}

type testBodyBind struct {
Type string `uri:"type"`
}

type testBodyReq struct {
url string
got interface{}
need interface{}
}

func TestBindBody(t *testing.T) {
router := func() *gin.Engine {
router := gin.Default()
Expand Down Expand Up @@ -660,6 +667,8 @@ func TestBindBody(t *testing.T) {
c.String(200, "string")
case "bytes":
c.String(200, "bytes")
case "io.writer":
c.String(200, "io.writer")
default:
c.String(500, "unknown")
}
Expand All @@ -669,77 +678,34 @@ func TestBindBody(t *testing.T) {
}()

ts := httptest.NewServer(http.HandlerFunc(router.ServeHTTP))
code := 0

var u uint
err := New(nil).GET(ts.URL + "/uint").BindBody(&u).Code(&code).Do()
assert.Equal(t, u, uint(1))
assert.NoError(t, err)

var u8 uint8
err = New(nil).GET(ts.URL + "/uint8").BindBody(&u8).Code(&code).Do()
assert.Equal(t, u8, uint8(2))
assert.NoError(t, err)

var u16 uint16
err = New(nil).GET(ts.URL + "/uint16").BindBody(&u16).Code(&code).Do()
assert.Equal(t, u16, uint16(3))
assert.NoError(t, err)

var u32 uint32
err = New(nil).GET(ts.URL + "/uint32").BindBody(&u32).Code(&code).Do()
assert.Equal(t, u32, uint32(4))
assert.NoError(t, err)

var u64 uint64
err = New(nil).GET(ts.URL + "/uint64").BindBody(&u64).Code(&code).Do()
assert.Equal(t, u64, uint64(5))
assert.NoError(t, err)

var i int
err = New(nil).GET(ts.URL + "/int").BindBody(&i).Code(&code).Do()
assert.Equal(t, i, int(6))
assert.NoError(t, err)

var i8 int8
err = New(nil).GET(ts.URL + "/int8").BindBody(&i8).Code(&code).Do()
assert.Equal(t, i8, int8(7))
assert.NoError(t, err)

var i16 int16
err = New(nil).GET(ts.URL + "/int16").BindBody(&i16).Code(&code).Do()
assert.Equal(t, i16, int16(8))
assert.NoError(t, err)

var i32 int32
err = New(nil).GET(ts.URL + "/int32").BindBody(&i32).Code(&code).Do()
assert.Equal(t, i32, int32(9))
assert.NoError(t, err)

var i64 int64
err = New(nil).GET(ts.URL + "/int64").BindBody(&i64).Code(&code).Do()
assert.Equal(t, i64, int64(10))
assert.NoError(t, err)

var f32 float32
err = New(nil).GET(ts.URL + "/float32").BindBody(&f32).Code(&code).Do()
assert.Equal(t, f32, float32(11))
assert.NoError(t, err)
tests := []testBodyReq{
{url: "/uint", got: new(uint), need: core.NewPtrVal(uint(1))},
{url: "/uint8", got: new(uint8), need: core.NewPtrVal(uint8(2))},
{url: "/uint16", got: new(uint16), need: core.NewPtrVal(uint16(3))},
{url: "/uint32", got: new(uint32), need: core.NewPtrVal(uint32(4))},
{url: "/uint64", got: new(uint64), need: core.NewPtrVal(uint64(5))},
{url: "/int", got: new(int), need: core.NewPtrVal(int(6))},
{url: "/int8", got: new(int8), need: core.NewPtrVal(int8(7))},
{url: "/int16", got: new(int16), need: core.NewPtrVal(int16(8))},
{url: "/int32", got: new(int32), need: core.NewPtrVal(int32(9))},
{url: "/int64", got: new(int64), need: core.NewPtrVal(int64(10))},
{url: "/float32", got: new(float32), need: core.NewPtrVal(float32(11))},
{url: "/float64", got: new(float64), need: core.NewPtrVal(float64(12))},
{url: "/string", got: new(string), need: core.NewPtrVal("string")},
{url: "/bytes", got: new([]byte), need: core.NewPtrVal([]byte("bytes"))},
{url: "/io.writer", got: bytes.NewBufferString(""), need: bytes.NewBufferString("io.writer")},
}

var f64 float64
err = New(nil).GET(ts.URL + "/float64").BindBody(&f64).Code(&code).Do()
assert.Equal(t, f64, float64(12))
assert.NoError(t, err)
for _, v := range tests {

var s string
err = New(nil).GET(ts.URL + "/string").BindBody(&s).Code(&code).Do()
assert.Equal(t, s, "string")
assert.NoError(t, err)
code := 0
err := New(nil).GET(ts.URL + v.url).BindBody(v.got).Code(&code).Do()
assert.Equal(t, code, 200)
assert.NoError(t, err)
assert.Equal(t, v.got, v.need)
}

var b []byte
err = New(nil).GET(ts.URL + "/bytes").BindBody(&b).Code(&code).Do()
assert.Equal(t, b, []byte("bytes"))
assert.NoError(t, err)
}

func TestSetBody(t *testing.T) {
Expand Down Expand Up @@ -787,6 +753,8 @@ func TestSetBody(t *testing.T) {
assert.Equal(t, s, "11")
case testBody.Float64:
assert.Equal(t, s, "12")
case testBody.Reader:
assert.Equal(t, s, "test io.Reader")
default:
c.JSON(500, "unknown type")
}
Expand Down Expand Up @@ -855,6 +823,11 @@ func TestSetBody(t *testing.T) {
err = New(nil).POST(ts.URL).SetQuery(H{"bytes": true}).SetBody([]byte("test bytes")).Code(&code).Do()
assert.NoError(t, err)
assert.Equal(t, code, 200)

// test io.Reader
err = New(nil).POST(ts.URL).SetQuery(H{"reader": true}).SetBody(bytes.NewBufferString("test io.Reader")).Code(&code).Do()
assert.NoError(t, err)
assert.Equal(t, code, 200)
}

func setupProxy(t *testing.T) *gin.Engine {
Expand Down

0 comments on commit 4501526

Please sign in to comment.