在传统单体架构中,由于应用动态性不强,不会频繁的更新和发布,也不会进行自动伸缩,我们通常将所有的服务地址都直接写在项目的配置文件中,发生变化时,手动改一下配置文件,也不会觉得有什么问题。但是在微服务模式下,服务会更细的拆分解耦,微服务会被频繁的更新和发布,根据负载情况进行动态伸缩,以及受资源调度影响而从一台服务器迁移到另一台服务器等等。总而言之,在微服务架构中,微服务实例的网络位置变化是一种常态,服务发现也就成了微服务中的一个至关重要的环节。
服务发现是什么其实,服务发现可以说自古有之,我们每天在不知不觉中就一直在使用服务发现。比如,我们在浏览器中输入域名,DNS服务器会根据我们的域名解析出一个Ip地址,然后去请求这个Ip来获取我们想要的数据,又或是我们使用网络打印机的时候,首先要通过WS-Discovery或者Bonjour协议来发现并连接网络中存在的打印服务等。这都是服务发现,它可以让我们只需说我想要什么服务即可,而不必去关心服务提供者的具体网络位置(IP 地址、端口等)。
目前,服务发现主要分为两种模式,客户端模式与服务端模式,两者的本质区别在于,客户端是否保存服务列表信息,比如DNS就属于服务端模式。
在客户端模式下,如果要进行微服务调用,首先要到服务注册中心获取服务列表,然后使用本地的负载均衡策略选择一个服务进行调用。
而在服务端模式下,客户端直接向服务注册中心发送请求,服务注册中心再通过自身负载均衡策略对微服务进行调用后返回给客户端。
客户端模式相对来说比较简单,也比较容易实现,本文就先来介绍一下基于Consul的客户端服务发现。
Consul简介Consul是HashiCorp公司推出的使用go语言开发的开源工具,用于实现分布式系统的服务发现与配置,内置了服务注册与发现框架、分布一致性协议实现、健康检查、Key/Value存储、多数据中心方案,使用起来较为简单。
Consul的安装包仅包含一个可执行文件,部署非常方便,直接从 官网) 下载即可。
如图,可以看出Consul的集群是由N个Server,加上M个Client组成的。而不管是Server还是Client,都是Consul的一个节点,所有的服务都可以注册到这些节点上,正是通过这些节点实现服务注册信息的共享。
Consule的核心概念:
Server:表示Consul的server模式,它会把所有的信息持久化的本地,这样遇到故障,信息是可以被保留的。
Client:表示consul的client模式,就是客户端模式。在这种模式下,所有注册到当前节点的服务会被转发到server,本身不持久化这些信息。
ServerLeader:上图那个Server下面有LEADER标识的,表明这个Server是它们的老大,它和其它Server不一样的是,它需要负责同步注册的信息给其它的Server,同时也要负责各个节点的健康监测。
关于Consul集群搭建等文章非常之多,本文就不再啰嗦,简单使用开发模式来演示,运行如下命令:
./consul agent -dev # 输出 ==> Starting Consul agent... ==> Consul agent running! Version: 'v1.4.0' Node ID: '21ec5df7-f11d-3a4e-ad1b-5ca445f8149b' Node name: 'Cosmos' Datacenter: 'dc1' (Segment: '<all>') Server: true (Bootstrap: false) Client Addr: [127.0.0.1] (HTTP: 8500, HTTPS: -1, gRPC: 8502, DNS: 8600) Cluster Addr: 127.0.0.1 (LAN: 8301, WAN: 8302) Encrypt: Gossip: false, TLS-Outgoing: false, TLS-Incoming: false如上,可以看到Consul默认的几个端口,如8500是客户端基于Http调用的,也是我们最常用的,另外再补充一下常用的几个参数的含义:
-dev:创建一个开发环境下的server节点,不会有任何持久化操作,不建议在生产环境中使用。
-bootstrap-expect:该命令通知consul server准备加入的server节点个数,延迟日志复制的启动,直到指定数量的server节点成功的加入后才启动。
-client: 用于客户端通过RPC, DNS, HTTP 或 HTTPS访问,默认127.0.0.1。
-bind: 用于集群间通信,默认0.0.0.0。
-advertise: 通告地址,通告给集群中其他节点,默认使用 -bind 地址。
注册服务我们首先创建一个ASP.NET Core WebAPI程序,命名为ServiceA。
然后引入Cosnul的官方Nuge包:
dotnet add package ConsulConsul包中提供了一个IConsulClient类,我们可以通过它来调用Consul进行服务的注册,以及发现等。