函数封装
// @see https://studygolang.com/articles/21194?fr=sidebar
// @see https://github.com/GeraltXLi/go-tools/tree/master/http
// 该参考地址另有封装的GET, POST请求等方法
// HttpClient 注意client 本身是连接池,不要每次请求时创建client
var (
HttpClient *http.Client
)
func InitHttpClient() {
HttpClient = &http.Client{
Timeout: 30 * time.Second, // 请求超时时间
}
}
// UploadFile 发送文件上传请求
func UploadFile(url string, params map[string]string, nameField, filename string, file io.Reader) ([]byte, error) {
body := new(bytes.Buffer)
writer := multipart.NewWriter(body)
// 在表单中创建一个文件字段
formFile, err := writer.CreateFormFile(nameField, filename)
if err != nil {
return nil, err
}
// 读取文件内容到表单文件字段
_, err = io.Copy(formFile, file)
if err != nil {
return nil, err
}
// 将其他参数写入到表单
for key, val := range params {
_ = writer.WriteField(key, val)
}
if err = writer.Close(); err != nil {
return nil, err
}
// 构造请求对象
req, err := http.NewRequest("POST", url, body)
if err != nil {
return nil, err
}
//req.Header.Set("Content-Type","multipart/form-data")
req.Header.Add("Content-Type", writer.FormDataContentType())
// 发送请求
resp, err := HttpClient.Do(req)
if err != nil {
return nil, err
}
defer resp.Body.Close()
return ioutil.ReadAll(resp.Body)
}
调用方法
utils.InitHttpClient()
// 要上传的文件地址
filePath := `D:\wwwroot\example.txt`
// 打开文件句柄
srcFile, err := os.Open(filePath)
if err != nil {
fmt.Println("os.Open.err", err)
}
// 文件上传时的额外参数
params := map[string]string{
"param": `example`,
}
_, err = utils.UploadFile(`http://127.0.0.1:8080/uploadFile`, params, "file", "example.txt", srcFile)
if err != nil {
fmt.Println("UploadFile.err", err)
} else {
fmt.Println("UploadFile.success", string(resp))
}
调用方法(批量上传)
var fileList []FileInfo
GetFileList(path, &fileList)
fmt.Println("文件数量:", len(fileList))
fmt.Println("begin:", time.Now())
// 批量上传只需要初始化一次请求池
utils.InitHttpClient()
// 遍历文件上传
for _, file := range fileList {
fmt.Println("file", file.Name, file.Size, file.Path)
// 打开文件句柄
srcFile, err := os.Open(file.Path)
if err != nil {
fmt.Println("os.Open.err", file.Name, err)
}
// todo: 增加文件大小和md5/sha1校验值
// 文件上传时的额外参数
params := map[string]string{
//name: file.Name,
//size: strconv.FormatInt(file.Size, 10),
"path": strings.Replace(file.Path[len(path):], `\`, `/`, -1),
}
_, err = utils.UploadFile(global.Config.ServerUrl, params, "file", file.Name, srcFile)
if err != nil {
fmt.Println("UploadFile.err", file.Name, err)
} else {
//fmt.Println("UploadFile.success", file.Name, string(resp))
}
}
fmt.Println("end:", time.Now())