中间件是接收并返回http.Handler的函数,用于在请求前后执行日志、认证等通用逻辑。通过嵌套组合或使用chi等库的Use方法,可构建灵活的HTTP服务处理链。

在Go语言中实现HTTP服务器中间件,核心思路是利用函数包装(Wrap Function)机制,对请求处理链进行增强。中间件通常用于日志记录、身份验证、跨域处理、错误恢复等通用功能,通过组合多个中间件,可以构建灵活且可维护的服务。
什么是中间件
中间件是一个函数,它接收一个 http.Handler 并返回一个新的 http.Handler。它可以在目标处理器执行前后插入逻辑,比如修改请求、记录时间、检查权限等。
Go 的 http.Handler 接口是中间件设计的基础:
type Handler interface {
ServeHTTP(w http.ResponseWriter, r *http.Request)
}
因此,中间件函数签名通常是:
立即学习“go语言免费学习笔记(深入)”;
func Middleware(next http.Handler) http.Handler
编写基础中间件示例
以下是一些常见中间件的实现方式:
1. 日志中间件
func loggingMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
log.Printf(“%s %s”, r.Method, r.URL.Path)
next.ServeHTTP(w, r)
})
}
2. 身份验证中间件
func authMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
token := r.Header.Get(“Authorization”)
if token == “” {
http.Error(w, “Unauthorized”, http.StatusUnauthorized)
return
}
// 这里可加入 JWT 验证等逻辑
next.ServeHTTP(w, r)
})
}
3. 错误恢复中间件

百度大模型语义搜索体验中心
22
查看详情
func recoverMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
defer func() {
if err := recover(); err != nil {
log.Printf(“Panic: %v”, err)
http.Error(w, “Internal Server Error”, http.StatusInternalServerError)
}
}()
next.ServeHTTP(w, r)
})
}
组合多个中间件
中间件可以逐层嵌套使用。最内层是最终的业务处理器,外层是各个中间件。
handler := http.HandlerFunc(helloHandler)
handler = loggingMiddleware(handler)
handler = authMiddleware(handler)
handler = recoverMiddleware(handler)
http.Handle(“/hello”, handler)
http.ListenAndServe(“:8080”, nil)
也可以写成一行:
http.Handle(“/hello”,
recoverMiddleware(
authMiddleware(
loggingMiddleware(http.HandlerFunc(helloHandler)))))
如果想更简洁,可以自己实现一个 Use 函数来链式组合中间件。
使用第三方库简化操作
虽然标准库足够实现中间件,但像 gorilla/mux 或 chi 这类路由器提供了更方便的中间件支持。
例如使用 chi:
r := chi.NewRouter()
r.Use(loggingMiddleware)
r.Use(authMiddleware)
r.Get(“/hello”, helloHandler)
http.ListenAndServe(“:8080”, r)
chi 的 Use 方法会自动将中间件应用到后续注册的路由上,结构更清晰。
基本上就这些。Golang 的中间件机制不依赖框架,靠的是对 http.Handler 的理解和函数式编程思想。只要掌握包装模式,就能自由构建所需功能。
大家都在看:
深入理解Go语言的defer机制:原理、限制与替代方案
Go与Fish Shell集成指南:正确设置GOPATH以避免包导入错误
使用 Go 语言进行原始套接字编程
Go语言defer机制深度解析:能否获取其函数引用?

































暂无评论内容