中间件注册顺序即执行顺序,fiber无优先级字段,app.use()调用顺序决定全局中间件执行先后;路由级中间件在全局之后、handler之前按参数顺序执行;返回阶段逆序执行,需注意资源清理与日志补全。

中间件注册顺序就是执行顺序,Fiber 不提供优先级字段或运行时重排能力,必须靠代码书写顺序硬控。
app.Use() 调用顺序决定全局中间件执行先后
Fiber 把所有 app.Use() 注册的中间件按调用顺序存入切片,请求进来时逐个执行。先写的中间件先拿到 *fiber.Ctx,后写的在它之后、handler 之前执行。
- 错误写法:
app.Use(authMiddleware); app.Use(logger.New())→ 日志里看不到未通过鉴权的请求 - 正确写法:
app.Use(logger.New()); app.Use(authMiddleware)→ 所有请求都打日志,再走鉴权 - 注意:
app.Use("/api", cors.New())这种带前缀的,只影响匹配/api开头的路径,但执行时机仍遵循全局注册顺序
路由级中间件插入位置影响嵌套层级
单个路由上用 app.Get("/x", mwA, mwB, handler),这些中间件会在所有 app.Use() 之后、handler 之前执行,且按参数顺序串行调用。
-
mwA和mwB是“局部中间件”,只对这条路由生效 - 它们的执行时机晚于所有
app.Use(),但早于handler;返回阶段则相反:handler ← mwB ← mwA ← 全局中间件 - 常见坑:
mwA里设了c.Locals("user", u),mwB却没做类型断言就直接用,会 panic
混合使用时执行链是严格线性的
全局 + 路由组 + 单路由三级嵌套,不是“作用域叠加”,而是函数嵌套式调用链,顺序完全由代码位置决定。
- 示例链路:
app.Use(logger)→api := app.Group("/api", jwtAuth)→api.Get("/data", ipWhitelist, h) - 实际执行流:
logger→jwtAuth→ipWhitelist→h→ipWhitelist(返回) →jwtAuth(返回) →logger(返回) - 关键点:没有“并行生效”或“条件跳过”,哪怕
jwtAuthAbort() 了,logger的返回逻辑仍会执行(但可能拿不到响应体)
最容易被忽略的是返回阶段的逆序执行——很多中间件只写了前置逻辑,忘了在返回路径上清理资源或补全日志,导致指标错乱或上下文泄漏。











