必须用fiber.New()而非fiber.Default(),因后者默认启用Logger(泄露Authorization等敏感头)、Recover(暴露panic堆栈)和RequestID(无采样白耗资源),且中间件顺序失控易覆盖响应头;正确做法是fiber.New()显式初始化并按需注册中间件。

fiber.New() 是唯一安全的起点,fiber.Default() 不该出现在生产代码里——它默认开启日志、panic 恢复和请求 ID 注入,会泄露敏感头、拖慢 TTFB 0.3–0.8ms,且中间件顺序失控时可能覆盖响应。
为什么必须用 fiber.New() 而不是 fiber.Default()
你不是在“少用功能”,而是在避免默认行为引发的线上事故:
-
fiber.Default()自动挂载Logger:每条请求全量打日志(含 header、body),Authorization、Cookie 等敏感字段裸奔 - 自动启用
Recover:panic 后返回 500 + 完整堆栈,前端可直接看到源码路径、变量名甚至行号 - 自动注入
RequestID:若没对接 tracing 系统或配置采样率,只是白占内存和带宽 - 所有中间件共享一个
*fiber.Ctx实例,顺序错一位就可能提前写响应体、覆盖X-Request-ID头
正确姿势是显式初始化:app := fiber.New(&fiber.Config{CaseSensitive: true, StrictRouting: true}),再按需注册中间件。
StrictRouting 导致 /users 和 /users/ 都 404?这不是 bug
Fiber 默认把两者视为不同路径。你只注册了 app.Get("/users", handler),那么 GET /users/ 必然 404——这不是框架缺陷,而是路由契约。
- 别关
StrictRouting: false:关掉后,/users/123可能被/users匹配,c.Params("id")拿不到值 - 显式注册两条路由:
app.Get("/users", handler)和app.Get("/users/", redirectHandler) - 或加统一重定向中间件:
if strings.HasSuffix(c.Path(), "/") && c.Path() != "/" { c.Redirect(strings.TrimSuffix(c.Path(), "/"), 301) } - 上线前同步检查 OpenAPI spec、前端 SDK、Postman 集合是否全用无尾斜杠路径
c.Params()、c.QueryParam()、c.BodyParser() 别混着用
三者来源完全隔离,错一个就空值:
-
c.Params("id")只读路径占位符,比如app.Get("/user/:id")匹配/user/123后的"123";对?id=123或 JSON body 无效 -
c.QueryParam("q")只读 query string,如/search?q=go中的"go";不解析路径、body、header -
c.FormValue("name")是给application/x-www-form-urlencoded准备的;JSON 必须用c.BodyParser(&v)
常见错误是 handler 里同时调用 c.Params("id") 和 c.QueryParam("id"),以为能兜底,实际只是两个空字符串。
中间件注册顺序决定一切,尤其 prom.Handler() 和 /metrics
prom.Handler() 必须在任何业务路由注册前调用,否则 /metrics 返回 404 或空响应:
- 正确顺序:
app.Use(prom.Handler())→app.Get("/api/users", handler)→app.Get("/metrics", prom.Handler()) - 别把它放在
app.Static()、app.All("/*", ...)或权限中间件之后——这些会拦截/metrics请求,导致指标漏采 - 验证方法:
curl -v http://localhost:3000/metrics,确认状态码是 200,Content-Type是text/plain; version=0.0.4 - 临时调试:把
app.Get("/metrics", ...)改成app.Get("/debug/metrics", ...)绕过通配路由,确认指标能出来再调顺序
最易被忽略的是:Fiber 中间件执行顺序严格按代码调用顺序,一旦某个中间件提前 c.SendStatus(401).Send() 或直接 return,后续所有中间件(包括指标收集)都会被跳过。











