gin基础学习笔记(二)

1. 上传单个文件

  • multipart/form-data格式用于文件上传

  • gin文件上传与原生的net/http方法类似,不同在于gin把原生的request封装到c.Request中

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>
<body>
    <form action="http://localhost:8080/upload" method="post" enctype="multipart/form-data">
          上传文件:<input type="file" name="file" >
          <input type="submit" value="提交">
    </form>
</body>
</html>

在 Go 语言中,<< 是位运算符,表示按位左移操作。8 << 20 的含义是将整数 8 左移 20 位,即将二进制表示的数值 8 左移 20 位。

在这种情况下,8 的二进制表示是 0000 1000,将其左移 20 位后,即在低位添加 20 个 0,结果为 1000 0000 0000 0000 0000 0000 0000

将这个二进制数转换为十进制数,即为 8388608。因此,在 Go 中,8 << 20 的结果为 8388608

8 << 20 表示将整数 8 左移 20 位,结果为 8388608这个值代表的是字节数。要将字节数转换为兆字节(MB),可以使用以下公式:

{MB} = {字节数} /{1024* 1024} 

将 8388608 字节代入公式中:

MB = 8388608 / (1024 * 1024) = 8 \text{ MB} ]

因此,在这种情况下,r.MaxMultipartMemory = 8 << 20 表示 MaxMultipartMemory 的值被设置为 8 MB

package main

import (
	"fmt"
	"net/http"

	"github.com/gin-gonic/gin"
)

func main() {
	// 1.创建路由
	// 默认使用了两个中间件Logger(),Recovery()
	r := gin.Default()
	// 2.绑定路由规则,执行的函数
	// gin.Context,封装了request和response
	r.POST("/form", func(c *gin.Context) {
		types := c.DefaultPostForm("type", "post")
		username := c.PostForm("username")
		pwd := c.PostForm("userpassword")
		c.String(http.StatusOK, fmt.Sprintf("username: %s, pwd: %s, type: %s", username, pwd, types))
	})
	// 规定最大上传尺寸 8MB
	r.MaxMultipartMemory = 8 << 20

	r.POST("/upload", func(c *gin.Context) {
		file, err := c.FormFile("file") // 从请求中获取上传的文件
		// 指定路径名
		uploadPath := "./file/" + file.Filename
		if err != nil {
			c.String(500, "上传图片错误") // 如果获取文件出错,返回500 状态码 和错误信息
		}
		downerr := c.SaveUploadedFile(file, uploadPath) //保存上传的文件到服务器的指定路径
		if downerr != nil {
			// 保存文件时出错
			c.String(http.StatusInternalServerError, "保存文件失败")
		} else {
			// 文件保存成功
			c.String(http.StatusOK, "文件下载成功,保存路径为:"+uploadPath) //在上传成功后,返回状态码 200(http.StatusOK)和上传成功的文件名。

		}

	})

	// 3.监听端口,默认在8080
	// Run("里面不指定端口号默认为8080")
	r.Run()
}

2.上传指定文件

gin里没有专门的函数,所以需要后端把上传的文件命进行判断处理

package main

import (
	"fmt"
	"net/http"

	"github.com/gin-gonic/gin"
)

func main() {

	r := gin.Default()

	r.MaxMultipartMemory = 8 << 20

	r.POST("/upload2", func(c *gin.Context) {

		_, headers, err := c.Request.FormFile("file")
		if err != nil {
			c.String(http.StatusOK, fmt.Sprintf(" Error when try to get file : %v", err))
		}

		// herders.Size 获取文件大小
		if headers.Size > 1024*1024*2 {
			c.String(http.StatusOK, "文件太大了")
			return
		}

		// headers.Herder.Get("Content-Type")获取上传文件的类型
		if headers.Header.Get("Content-Type") != "image/png" {
			fmt.Println("只能上传png")
			return
		}
		c.SaveUploadedFile(headers, "./video/"+headers.Filename)
		c.String(http.StatusOK, headers.Filename)

	})

	r.Run()
}

上传正确的格式和文件大小

错误上传文件格式

报错

我重新写一遍后端的时候容易遗忘漏掉 r.Run() 函数,那么启动main.go的过程中会出现如下报错

[GIN-debug] [WARNING] Creating an Engine instance with the Logger and Recovery middleware already attached.

[GIN-debug] [WARNING] Running in "debug" mode. Switch to "release" mode in production.
 - using env:   export GIN_MODE=release
 - using code:  gin.SetMode(gin.ReleaseMode)

[GIN-debug] POST   /upload2                  --> main.main.func1 (3 handlers)

养成好习惯,先写 r.Run()

  • 16
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值