一、 Next()
和 Abort()
的含義
-
Next()
的含義語法:
func (c *Context) Next()
英文原文
Next should be used only inside middleware. It executes the pending handlers in the chain inside the calling handler.
大意:Next 應該僅可以在中間件中使用,它在調用的函數中的鏈中執行掛起的函數。
-
Abort()
的含義語法:
func (c *Context)Abort()
英文原文
Abort prevents pending handlers from being called. Note that this will not stop the current handler. Let's say you have an authorization middleware that validates that the current request is authorized. If the authorization fails (ex: the password does not match), call Abort to ensure the remaining handlers for this request are not called.
大意:Abort 在被調用的函數中阻止掛起函數。注意這將不會停止當前的函數。例如,你有一個驗證當前的請求是否是認證過的 Authorization 中間件。如果驗證失敗(例如,密碼不匹配),調用 Abort 以確保這個請求的其他函數不會被調用。
二、示例分析
func main(){
router := gin.Default()
router.Use(middleware.FirstMiddleware(), middleware.SecondMiddleware()) // (1)
router.Run()
}
func FirstMiddleware() gin.HandlerFunc {
return func( c *gin.Context) {
fmt.Println("first middleware before next()")
isAbort := c.Query("isAbort")
bAbort, err := strconv.ParseBool(isAbort)
if err != nil {
fmt.Printf("is abort value err, value %s\n", isAbort)
c.Next() // (2)
}
if bAbort {
fmt.Println("first middleware abort") //(3)
c.Abort()
//c.AbortWithStatusJSON(http.StatusOK, "abort is true")
return
} else {
fmt.Println("first middleware doesnot abort") //(4)
return
}
fmt.Println("first middleware after next()")
}
}
func SecondMiddleware() gin.HandlerFunc {
return func(c *gin.Context) {
fmt.Println("current inside of second middleware")
}
}
-
在調用時傳遞的
isAbort()
的值不能解析爲布爾類型的值時,會執行到 (2) 處。此時調用的是Next()
方法。由第一部分的內容可知。它執行掛起的函數,即在 (1) 處指定的函數,即SecondMiddleware()
,最後執行真正的業務處理函數,程序打印:first middleware before next() is abort value err, value d current inside of second middleware inner hello first middleware after next()
由上面的打印可知,程序在執行完業務處理後仍然會回到當前的函數。然後打印其他的內容。在使用的過程中,可以根據其餘部分是否繼續執行而在
c.Next()
後添加return
語句。 -
在調用時傳遞的
isAbort()
的值如果是可以解析爲布爾類型的值時,如果值爲真,則執行到 (3) 處。由於此處調用了Abort()
,根據第一部分的內容可知,它阻止了鏈中後續的函數的調用。所以SecondMiddleware
函數和業務函數Hello()
函數不會被調用。但它不能停止當前的函數,故其下面的打印仍會打印first middleware before next() first middleware abort first middleware after next()
注意: Abort()
和
AbortWithStatusJSON` 一直都是中止鏈的調用,不同之處在於,前者不會返回給前端任何內容,而後者則可以返回給前端一個JSON串。 -
在調用時傳遞的
isAbort()
的值可以解析爲布爾類型,如果值爲假,則流程會進入到 (4)處。它只是在當前的函數調用中返回,不會對整個鏈造成影響。first middleware before next() first middleware doesnot abort current inside of second middleware inner hello
參考鏈接:
[1] Failed to Abort() context - gin