在上一节文章 go使用net/http 创建web服务器-高阶篇
我们学会了创建 服务器。
在一般的C/S架构中,在多个客户端与服务器进行通信时,我们经常使用中间件,来出来一些,在业务逻辑之前的,客户端发送给服务器的数据验证。
一、什么是http中间件
在互联网的http通信中,如果多个客户端访问服务器,我们就会构建一个 client/server 客户端/服务器 架构来实现。
服务器用来接受客户端的请求,然后返回特定的资源或者数据给客户端。
中间件是客户端请求到达处理方法之前对其进行预处理的一些逻辑。
常用的应用场景有:
- 客户端身份校验
- 用户鉴权
- 客户端对服务器提供的特定服务是否有访问权限
- 验证用户 session,并保持通信存活
- 客户端请求参数解密
- 客户端参数格式化
- 日志记录器,用于记录每个 REST API 访问请求
- 跨域配置
- 返回数据格式化
- Header设置
二、中间件原理
在 Go 语言中,中间件 Handler 是封装另一个 http.Handler 以对请求进行预处理或后续处理的 http.Handler。它介于 Go Web 服务器与实际的处理程序之间,因此被称为“中间件”。
原理分析:
我们先看一个最简单的一个http服务器
package main
import (
"fmt"
"net/http"
)
func index(w http.ResponseWriter, r *http.Request) {
fmt.Fprintln(w, "Hello World")
}
func main() {
http.HandleFunc("/index", index)
http.ListenAndServe(":8090", nil)
}
上面的示例代码就实现了一个 http服务器。
在路由的处理方面,主要是 通过http.HandleFunc函数,我们可以看一下官方的源代码
// HandleFunc registers the handler function for the given pattern
// HandleFunc 注册handler处理函数到DefaultServeMux,用来绑定给定的url
// in the DefaultServeMux.
// The documentation for ServeMux explains how patterns are matched.
// ServeMux文档有详细的url解析匹配介绍
func HandleFunc(pattern string, handler func(ResponseWriter, *Request)) {
DefaultServeMux.HandleFunc(pattern, handler)
}
// HandleFunc registers the handler function for the given pattern.
func (mux *ServeMux) HandleFunc(pattern string, handler func(ResponseWriter, *Request)) {
if handler == nil {
panic("http: nil handler")
}
mux.Handle(pattern, HandlerFunc(handler))
}
// The HandlerFunc type is an adapter to allow the use of
// ordinary functions as HTTP handlers. If f is a function
// with the appropriate signature, HandlerFunc(f) is a
// Handler that calls f.
type HandlerFunc func(ResponseWriter, *Request)
// ServeHTTP calls f(w, r).
func (f HandlerFunc) ServeHTTP(w ResponseWriter, r *Request) {
f(w, r)
}
我们可以看到最后的处理是通过 HandlerFunc 反射。
这个正是我们传过去的index(w http.ResponseWriter, r *http.Request)
三、代码实现 middleware中间件
我们实现了一个 简单的 中间件日志 代码如下:
package main
import (
"fmt"
"log"
"net/http"
)
// middlewareLog中间件日志,用来记录每个请求,写进日子
func middlewareLog(handler http.HandlerFunc) http.HandlerFunc {
return func(writer http.ResponseWriter, request *http.Request) {
// 日志中间件
log.Println(request.Header)
handler(writer, request)
}
}
func index(w http.ResponseWriter, r *http.Request) {
_, _ = fmt.Fprintln(w, "Hello World")
}
func main() {
http.HandleFunc("/index", middlewareLog(index))
_ = http.ListenAndServe(":8090", nil)
}
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。