1. 程式人生 > 其它 >5-Gin上傳檔案

5-Gin上傳檔案

一 上傳檔案

1.1 上傳單個檔案

  • multipart/form-data格式用於檔案上傳
  • gin檔案上傳與原生的net/http方法類似,不同在於gin把原生的request封裝到c.Request中
package main

import (
	"github.com/gin-gonic/gin"
	"net/http"
)

func main() {
	r := gin.Default()
	//限制上傳最大尺寸 8 M,預設:gin.defaultMultipartMemory,32M
  // 8*2的20次方:8388608b也就是8M
	r.MaxMultipartMemory = 8 << 20
	r.POST("/upload", func(c *gin.Context) {
		file, err := c.FormFile("file")
		if err != nil {
			c.String(500, "上傳圖片出錯")
		}
    // 上傳檔案到指定的目錄,在專案根路徑下建立/media/upload資料夾
		dst := path.Join("./media/upload", file.Filename)
		fmt.Println(dst)
		c.SaveUploadedFile(file,dst)
		c.String(http.StatusOK, file.Filename)
	})
	r.Run()
}

1.2 上傳多個檔案之不同名

package main

import (
	"github.com/gin-gonic/gin"
	"net/http"
	"path"
)

func main() {
	router := gin.Default()

	router.MaxMultipartMemory = 8 << 20
	router.POST("/upload", func(c *gin.Context) {
		file1, _ := c.FormFile("file1")
		file2, _ := c.FormFile("file2")
		dst1 := path.Join("./media/upload", file1.Filename)
		c.SaveUploadedFile(file1,dst1)

		dst2 := path.Join("./media/upload", file2.Filename)
		c.SaveUploadedFile(file2,dst2)
		c.String(http.StatusOK, "檔案上傳成功")
	})
	router.Run(":8000")
}

1.3 上傳多個檔案之同名

package main

import (
	"fmt"
	"github.com/gin-gonic/gin"
	"net/http"
	"path"
)

func main() {
	router := gin.Default()

	router.MaxMultipartMemory = 8 << 20
	router.POST("/upload", func(c *gin.Context) {
		form, err := c.MultipartForm()
		if err != nil {
			c.String(http.StatusBadRequest, fmt.Sprintf("get err %s", err.Error()))
		}
		// 獲取所有圖片
		files := form.File["files"]
		// 遍歷所有圖片
		for _, file := range files {
			// 上傳檔案至指定目錄
			dst := path.Join("./media/upload", file.Filename)
			if err := c.SaveUploadedFile(file, dst); err != nil {
				c.String(http.StatusBadRequest, fmt.Sprintf("上傳失敗 %s", err.Error()))
				return
			}
		}
		c.String(200, fmt.Sprintf("上傳 %d 個檔案", len(files)))
	})
	router.Run(":8000")
}

1.4 上傳多個圖片-按照歸檔儲存

package main

import (
	"fmt"
	"gin_test/utils"
	"github.com/gin-gonic/gin"
	"log"
	"os"
	"path"
	"strconv"
)

func main() {
	router := gin.Default()

	router.MaxMultipartMemory = 8 << 20
	router.POST("/upload", func(c *gin.Context) {
		file, _ := c.FormFile("file")
		//2、獲取字尾名 判斷型別是否正確 .jpg .png .gif .jpeg .md
		extName := path.Ext(file.Filename) //獲取字尾名
		allowExtMap := map[string]bool{
			".jpg":  true,
			".png":  true,
			".gif":  true,
			".jpeg": true,
			".md": true,
		}

		if _, ok := allowExtMap[extName]; !ok {
			c.String(200, "檔案型別不合法")
			return
		}
		//3、建立圖片儲存目錄 static/upload/20200623
		day := utils.GetDay()
		dir := "./media/" + day
		if err := os.MkdirAll(dir, 0777); err != nil {
			log.Println(err)
		}
		//4、生成檔名稱 1649450399.md
		fileUnixName := strconv.FormatInt(utils.GetUnix(), 10)
		saveDir := path.Join(dir, fileUnixName+extName) // media/upload/20220409/1649450399.md
		fmt.Println(saveDir)
		c.SaveUploadedFile(file, saveDir)
		c.String(200, "上傳檔案成功")
	})
	router.Run(":8000")
}

utils/common.go

package utils

import (
	"crypto/md5"
	"fmt"
	"time"
)

//時間戳間戳轉換成日期
func UnixToDate(timestamp int) string {
	t := time.Unix(int64(timestamp), 0)
	return t.Format("2006-01-02 15:04:05")
}

//日期轉換成時間戳 2006-01-02 15:04:05
func DateToUnix(str string) int64 {
	template := "2006-01-02 15:04:05"
	t, err := time.ParseInLocation(template, str, time.Local)
	if err != nil {
		return 0
	}
	return t.Unix()
}
func GetUnix() int64 {
	return time.Now().Unix()
}
func GetDate() string {
	template := "2006-01-02 15:04:05"
	return time.Now().Format(template)
}
func GetDay() string {
	template := "20060102"
	return time.Now().Format(template)
}
func Md5(str string) string {
	data := []byte(str)
	return fmt.Sprintf("%x\n", md5.Sum(data))
}


Mac,linux平臺下注意許可權,先編譯,sudo執行,資料夾才能順利建立