go gin中间件关于 c.next()、c.abort()和return的使用

c.netx()

  • 测试代码
go 复制代码
package main

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

func main() {
	g := gin.New()
	g.Use(middleware1(), middleware2())
	g.GET("/", func(c *gin.Context) {
		fmt.Println("process request")
		c.JSON(http.StatusOK, "hello,world!")
	})
	err := g.Run()
	if err != nil {
		log.Fatal(err)
	}
}
func middleware1() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware1 start")
		c.Next()
		fmt.Println("middleware1 end")
	}
}

func middleware2() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware2 start")
		c.Next()
		fmt.Println("middleware2 end")
	}
}
bash 复制代码
middleware1 start
middleware2 start
process request
middleware2 end
middleware1 end
  • 总结
    中间件的执行顺序是按照注册的顺序执行的,在中间件中使用 c.Next() 方法,会先执行c.Next() 前面的,然后将控制权传递给下一个中间件或处理器,最后按照相反顺序执行中间件c.Next() 后面的代码。

c.abort()

  • 测试代码
bash 复制代码
package main

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

func main() {
	g := gin.New()
	g.Use(middleware1(), middleware2(), middleware3())
	g.GET("/", func(c *gin.Context) {
		fmt.Println("process request")
		c.JSON(http.StatusOK, "hello,world!")
	})
	err := g.Run()
	if err != nil {
		log.Fatal(err)
	}
}
func middleware1() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware1 start")
		c.Next()
		fmt.Println("middleware1 end")
	}
}

func middleware2() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware2 start")
		c.Abort()
		fmt.Println("middleware2 end")
	}
}

func middleware3() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware3 start")
		c.Next()
		fmt.Println("middleware3 end")
	}
}
bash 复制代码
middleware1 start
middleware2 start
middleware2 end
middleware1 end
  • 总结
    中间件的执行顺序是按照注册顺序执行的,中间件可以通过 c.Abort() 来中止后续中间件或处理器的处理流程。

return

  • 测试代码
bash 复制代码
package main

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

func main() {
	g := gin.New()
	g.Use(middleware1(), middleware2(), middleware3())
	g.GET("/", func(c *gin.Context) {
		fmt.Println("process request")
		c.JSON(http.StatusOK, "hello,world!")
	})
	err := g.Run()
	if err != nil {
		log.Fatal(err)
	}
}
func middleware1() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware1 start")
		c.Next()
		fmt.Println("middleware1 end")
	}
}

func middleware2() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware2 start")
		return
		fmt.Println("middleware2 end")
	}
}

func middleware3() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware3 start")
		c.Next()
		fmt.Println("middleware3 end")
	}
}
bash 复制代码
middleware1 start
middleware2 start
middleware3 start
process request
middleware3 end
middleware1 end
  • 总结
    中间件的执行顺序是按照注册顺序执行的,中间件可以通过 retrurn 来中止当前中间件的后续处理流程。

c.abort() +return

  • 测试代码
bash 复制代码
package main

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

func main() {
	g := gin.New()
	g.Use(middleware1(), middleware2(), middleware3())
	g.GET("/", func(c *gin.Context) {
		fmt.Println("process request")
		c.JSON(http.StatusOK, "hello,world!")
	})
	err := g.Run()
	if err != nil {
		log.Fatal(err)
	}
}
func middleware1() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware1 start")
		c.Next()
		fmt.Println("middleware1 end")
	}
}

func middleware2() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware2 start")
		c.Abort()
		return
		fmt.Println("middleware2 end")
	}
}

func middleware3() gin.HandlerFunc {
	return func(c *gin.Context) {
		fmt.Println("middleware3 start")
		c.Next()
		fmt.Println("middleware3 end")
	}
}
bash 复制代码
middleware1 start
middleware2 start
middleware1 end
  • 总结
    中间件的执行顺序是按照注册顺序执行的,中间件可以通过 c.abort() + retrurn 来中止当前中间件,后续中间件和处理器的处理流程。
相关推荐
Bony-7 小时前
Go语言垃圾回收机制详解与图解
开发语言·后端·golang
吴老弟i19 小时前
Go 多版本管理实战指南
golang·go
Grassto1 天前
HTTP请求超时?大数据量下的网关超时问题处理方案,流式处理,附go语言实现
后端·http·golang·go
Paul_09201 天前
golang编程题2
开发语言·后端·golang
代码N年归来仍是新手村成员1 天前
【Go】从defer关键字到锁
开发语言·后端·golang
源代码•宸2 天前
Leetcode—746. 使用最小花费爬楼梯【简单】
后端·算法·leetcode·职场和发展·golang·记忆化搜索·动规
x70x802 天前
Go中nil的使用
开发语言·后端·golang
源代码•宸2 天前
Leetcode—47. 全排列 II【中等】
经验分享·后端·算法·leetcode·面试·golang·深度优先
漫漫求2 天前
Go的panic、defer、recover的关系
开发语言·后端·golang
Tony Bai2 天前
2025 Go 官方调查解读:91% 满意度背后的隐忧与 AI 时代的“双刃剑”
开发语言·后端·golang