-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathmultipart.go
146 lines (128 loc) · 3.22 KB
/
multipart.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
package easy_http
import (
"bytes"
"io"
"io/ioutil"
"mime/multipart"
)
type MultipartDateType int8
//MultipartDateType 的枚举
const (
MultipartDateTypeFile MultipartDateType = iota
MultipartDateTypeFormDate
MultipartDateTypeContent
)
//用于 post multipart 的接口
type IMultipart interface {
//实现 Read函数
io.Reader
//获取这次的 boundary 字符串
ContentType() string
}
type EasyMultipart struct {
//multipart 内容
buf *bytes.Buffer
//随机生成的用于multipart 的 boundary字符串
contentType string
}
func (m *EasyMultipart) ContentType() string {
return m.contentType
}
func (m *EasyMultipart) Read(p []byte) (n int, err error) {
return m.buf.Read(p)
}
//用于 `MultipartBuilder` 中的内容记录
type MultipartDateContent struct {
Type MultipartDateType
Content []byte
}
//用于构造一个 multipart
type MultipartBuilder struct {
content map[string]*MultipartDateContent
}
//初始化一个 multipart 构造器
func NewMultipartBuilder() *MultipartBuilder {
return &MultipartBuilder{
content: make(map[string]*MultipartDateContent),
}
}
//添加文件
//name upload时的name
//fileName 文件的路径+文件名
func (m *MultipartBuilder) AddFile(name, fileName string) *MultipartBuilder {
m.content[name] = &MultipartDateContent{
Type: MultipartDateTypeFile,
Content: []byte(fileName),
}
return m
}
//添加form-data数据
func (m *MultipartBuilder) AddFromDate(name, value string) *MultipartBuilder {
m.content[name] = &MultipartDateContent{
Type: MultipartDateTypeFormDate,
Content: []byte(value),
}
return m
}
//以map的形式 添加form-data数据, k=>form-data的name, v=>form-data的Valve
func (m *MultipartBuilder) FromDate(value map[string]string) *MultipartBuilder {
for k, v := range value {
m.content[k] = &MultipartDateContent{
Type: MultipartDateTypeFormDate,
Content: []byte(v),
}
}
return m
}
//添加[]byte, name, form-data的name
func (m *MultipartBuilder) AddBytes(name string, bytes []byte) *MultipartBuilder {
m.content[name] = &MultipartDateContent{
Type: MultipartDateTypeContent,
Content: bytes,
}
return m
}
//构造 MultipartDate
func (m *MultipartBuilder) Builder() (*EasyMultipart, error) {
buf := new(bytes.Buffer)
mulWriter := multipart.NewWriter(buf)
defer mulWriter.Close()
for name, content := range m.content {
switch content.Type {
case MultipartDateTypeFile:
//文件类型,读取文件,写入buf
formFile, err := mulWriter.CreateFormFile(name, name)
if err != nil {
return nil, err
}
file, err := ioutil.ReadFile(string(content.Content))
if err != nil {
return nil, err
}
_, err = formFile.Write(file)
if err != nil {
return nil, err
}
case MultipartDateTypeFormDate:
//form-data类型,直接写入
err := mulWriter.WriteField(name, string(content.Content))
if err != nil {
return nil, err
}
case MultipartDateTypeContent:
//[]byte 类型,当做文件写入
formFile, err := mulWriter.CreateFormFile(name, name)
if err != nil {
return nil, err
}
_, err = formFile.Write(content.Content)
if err != nil {
return nil, err
}
}
}
return &EasyMultipart{
buf: buf,
contentType: mulWriter.FormDataContentType(),
}, nil
}