Go语言web服务器之文件上传-文件句柄

文件上传这类操作一般出现在的网站中,如:保存会员头像。这里我们以上传图片为例,来说明一个web页面如何上传文件至go语言web服务器。

Go语言web服务器之文件上传

完成文件上传,我们需要做以下两个操作,

第一步、创建upload.html,用户通过这个页面来选择并上传文件,源码如下

<html>
<head>
<title>Go语言上传文件</title>
</head>
<body>
 <h1>Go语言上传文件</h1>
<form enctype="multipart/form-data" action="/upload" method="post">
 <div><input type="file" name="uploadfile" /></div>
<div><input type="submit" value="上传" /></div>
 <input type="hidden" name="token" value="{{.}}">
</form>
</body>
</html>

这里我们需要注意的是要想让表单可以上传文件,那么form中必须包含属性enctype="multipart/form-data"

第二步、定义web服务器端的处理过程upload,代码如下

func upload(w http.ResponseWriter, r *http.Request) {
 fmt.Println("method:", r.Method) //获取请求的方法
 if r.Method == "GET" {
 crutime := time.Now().Unix()
 h := md5.New()
 io.WriteString(h, strconv.FormatInt(crutime, 10))
 token := fmt.Sprintf("0", h.Sum(nil))
 t, _ := template.ParseFiles(".//html//template//upload.html")
 t.Execute(w, token)
 } else if r.Method == "POST" {
 token := r.Form.Get("token")
 //验证token的合法性
 if token != "" {
 tokenOK := false
 for v := range queue {
 if queue[v] == token {
 tokenOK = true
 break
 }
 }
 if !tokenOK {
 fmt.Fprintf(w, "页面异常")
 return
 }
 } else {
 //不存在token报错
 fmt.Fprintf(w, "页面异常")
 return
 }
 r.ParseMultipartForm(32 << 20) // 运算符<<是左移运算符,32 << 20表示32*(2的20次方)
 file, handler, err := r.FormFile("uploadfile")
 if err != nil {
 fmt.Println(err)
 return
 }
 defer file.Close()
 fmt.Fprintf(w, "", handler.Header)
 // 请在当前目录下创建uploadFile目录
 f, err := os.OpenFile(".//uploadFile//"+handler.Filename, os.O_WRONLY|os.O_CREATE, 0666)
 if err != nil {
 fmt.Println(err)
 return
 }
 defer f.Close()
 io.Copy(f, file)
 } else {
 fmt.Fprintf(w, "it is not support.")
 }
}
在main函数中增加路由绑定http.HandleFunc("/upload", upload)

这里需要说明的有两点,

1、服务器端处理上传的文件使用的是ParseMultipartForm,参数表示服务器分配的最大内存,当上传文件小于最大内存时上传文件被保存在服务内存中,如果超了则保存在临时文件。

2、另一个是获取上传文件句柄,是通过FormFile来实现的,接下来就可以使用Copy函数将文件写到服务器磁盘上了。

上传成功后服务器端返回上传请求头部,如图

Go语言web服务器之文件上传

原文地址:https://www.slvit.com/zdlDetail?id=75

推荐阅读