Go Micro 中的 API 网关实现 —— Micro API 底层源码剖析(下)


上篇分享学院君介绍了 Micro API 底层如何解析命令行参数并设置全局初始值,接下来,我们来看看 Micro API 网关启动之后,是如何将 HTTP 请求映射到对应的 API 处理器进行处理的。

Micro API 底层基于 gorilla/mux 包实现 HTTP 请求路由的分发,首先我们基于 mux 的 NewRouter 函数创建一个路由器并将其赋值给 HTTP 处理器 hr 是一个指针类型,所以 h 指向的是 r 的引用):

// create the router
var h http.Handler
r := mux.NewRouter()
h = r

然后经过一些服务端全局参数的设置后,传入这些全局参数来初始化服务:

service := micro.NewService(srvOpts...)

接下来,会注册 RPC 请求处理器:

log.Logf("Registering RPC Handler at %s", RPCPath)
r.HandleFunc(RPCPath, handler.RPC)

默认 RPC 请求路径是 /rpc,客户端需要通过这个路径发起 POST 请求,请求参数一般是 JSON 格式数据或者编码过的 RPC 表单请求(参考文档示例),处理器底层会将 RPC 请求转化为对 Go Micro 底层服务的请求,对应的处理器源码位于 micro/micro/internal/handler/rpc.go 中。

接下来,会初始化解析器并注册 API 请求处理器(以我们启动 API 网关时传入 --handler=api 参数为例):

   // 解析器参数
	ropts := []resolver.Option{
		resolver.WithNamespace(Namespace),
		resolver.WithHandler(Handler),
	}

	// 初始化默认解析器
	rr := rrmicro.NewResolver(ropts...)

	...

  // 注册 API 请求处理器
	switch Handler {
	...
	case "api":
		log.Logf("Registering API Request Handler at %s", APIPath)
		rt := regRouter.NewRouter(
			router.WithNamespace(Namespace),
			router.WithHandler(aapi.Handler),
			router.WithResolver(rr),
			router.WithRegistry(service.Options().Registry),
		)
		ap := aapi.NewHandler(
			ahandler.WithNamespace(Namespace),
			ahandler.WithRouter(rt),
			ahandler.WithService(service),
		)
		r.PathPrefix(APIPath).Handler(ap)
	...
	}

默认的命名空间是 go.micro.api,默认的解析器是 micro(对应源码位于 micro/go-micro/api/resolver/micro/micro.go),然后会传入上述初始化的参数到 regRouter.NewRouter 函数来创建新的 API 路由器(对应源码位于 micro/go-micro/api/router/registry/registry.go),再通过这个路由器实例和之前初始化的服务实例(包含默认 Registry、Transport、Broker、Client、Server 配置,以便后续通过这些配置根据服务名和请求参数对底层服务发起请求)来创建 API 处理器(对应源码位于 micro/go-micro/api/handler/api/api.go),最后,把 API 请求路径前缀和 API 处理器设置到之前创建的路由器 r 上。

最后,我们初始化用作 API 网关的 HTTP 服务器并启动它(对应源码位于 micro/go-micro/api/server/http/http.go):

api := httpapi.NewServer(Address)
api.Init(opts...)
api.Handle("/", h)

// Start API
if err := api.Start(); err != nil {
    log.Fatal(err)
}

当有 HTTP 请求过来时,该网关服务器就可以对其进行解析(通过上述初始化的 Resolver)和处理(通过 API 请求处理器处理),并将结果返回给客户端(相应源码位于 micro/go-micro/api/handler/api/api.goServeHTTP 方法,以协程方式启动服务器对客户端请求进行处理,底层服务调用逻辑和我们前面介绍的客户端服务发现原理一致),以上就是 Micro API 网关的底层实现源码,我们可以看到这个默认的 API 网关采用的是 API 网关架构模式的第一种模式:单节点网关模式,所有的 API 请求都会经过这个单一入口对底层服务进行请求。


点赞 取消点赞 收藏 取消收藏

<< 上一篇: Go Micro 中的 API 网关实现 —— Micro API 底层源码剖析(上)

>> 下一篇: 通过 Micro Web 仪表盘页面查看、测试 Go Micro 微服务接口