注册中心:Consul原理分析
Consul
Consul是一个高可用的分布式服务注册中心,由HashiCorp公司推出,Golang实现的开源共享的服务工具。Consul在分布式服务注册与发现方面有自己的特色,解决方案更加“一站式”,不再需要依赖其他工具。
- 
 1、通过HTTP接口和DNS协议调用API存储键值对,使服务注册和服务发现更容易; 2、支持健康检查,可以快速的告警在集群中的操作 3、支持key/value存储动态配置 4、支持任意数量的区域
Consul 中的概念
Consul安装
mac
brew tap hashicorp/tap brew install hashicorp/tap/consul
- 
 run
consul agent -server -ui -client 0.0.0.0 -bootstrap-expect=1 -data-dir=/Users/yichuan.deng/soft/consul/data -node=consul-01 -advertise=127.0.0.1 -datacenter SH-TMP -bind=0.0.0.0 -client=0.0.0.0 -log-file=/Users/yichuan.deng/soft/consul/consul.log
Go使用Consul
服务注册
package main
import (
   "fmt"
   "net/http"
   consulAPI "github.com/hashicorp/consul/api"
)
const (
   localIp   = "127.0.0.1"
   localPort = 81
)
func consulRegister() {
          
   
   // 创建连接consul服务配置
   config := consulAPI.DefaultConfig()
   config.Address = "0.0.0.0:8500"
   client, err := consulAPI.NewClient(config)
   if err != nil {
          
   
      fmt.Println("consul client error : ", err)
   }
   // 创建注册到consul的服务到
   registration := new(consulAPI.AgentServiceRegistration)
   registration.ID = "996"
   registration.Name = "service996"
   registration.Port = localPort
   registration.Tags = []string{
          
   "testService"}
   registration.Address = localIp
   // 增加consul健康检查回调函数
   check := new(consulAPI.AgentServiceCheck)
   check.HTTP = fmt.Sprintf("http://%s:%d", registration.Address, registration.Port)
   check.Timeout = "5s"
   check.Interval = "5s"
   check.DeregisterCriticalServiceAfter = "30s" // 故障检查失败30s后 consul自动将注册服务删除
   registration.Check = check
   // 注册服务到consul
   err = client.Agent().ServiceRegister(registration)
}
func Handler(w http.ResponseWriter, r *http.Request) {
          
   
   w.Write([]byte("health"))
   fmt.Println("health")
}
func main() {
          
   
   consulRegister()
   //定义一个http接口
   http.HandleFunc("/", Handler)
   err := http.ListenAndServe("0.0.0.0:81", nil)
   if err != nil {
          
   
      fmt.Println("error: ", err.Error())
   }
} 
可以看到,我们的HTTP服务一直被调用。在consul上也可以看到
服务发现
可以看到,我们在sleep 一分钟后,我们把service 退出之后,健康的service的列表就为空:[] 了。
package main
import (
   "fmt"
   "time"
   consulAPI "github.com/hashicorp/consul/api"
)
const (
   consulAgentAddress = "0.0.0.0:8500"
)
// ConsulFindServer 从consul中发现服务
func ConsulFindServer() {
   // 创建连接consul服务配置
   config := consulAPI.DefaultConfig()
   config.Address = consulAgentAddress
   client, err := consulAPI.NewClient(config)
   if err != nil {
      fmt.Println("consul client error : ", err)
      return
   }
   // 获取指定service
   service, _, err := client.Agent().Service("996", nil)
   if err != nil {
      return
   }
   fmt.Println(service.Address)
   fmt.Println(service.Port)
   time.Sleep(60 * time.Second)
   // 只获取健康的service
   serviceHealthy, _, err := client.Health().Service("service337", "", true, nil)
   if err != nil {
      return
   }
   fmt.Println(serviceHealthy)
}
func main() {
   ConsulFindServer()
} 
服务注册与发现
consul client(客户端)使用HTTP或DNS的方式将服务注册到consul server(服务端)注册中心中。服务请求方通过consul server发现他所依赖的服务。
健康检测
consul client提供对应用程序健康检查机制,并将健康检查状态上报给consul server集群,用来监控集群节点的运行状况,并及时下线不健康的节点。
