标签:服务 spring Consul 往下掉 ttl http consul cloud discovery
问题背景
问题的现象是生产的服务在部署到consul上面之后,一直往下掉
开始解决
首先介绍下生产的consul部署方式为 集群部署 3 server 3 client
生产consul运维搭建参考:
墨西哥CCP部署交付
具体的部署方案参考:
物理拓扑结构图
3个server节点 3个 client节点
|
域名
|
IP
|
|
server1
|
k8sm1
|
10.23.111.17
|
|
server2
|
k8sm2
|
10.23.111.44
|
|
server3
|
k8sm3
|
10.23.111.45
|
|
client1
|
k8sn4
|
10.23.111.21
|
|
client2
|
k8sn5
|
10.23.111.22
|
|
client3
|
k8sn6
|
10.23.111.51
|
|
以下为consul地址: https://consul-ccp.nanopay.mx/ui/
1、查看所有的机器情况
登陆任意一台机器执行:
1、能看到所有集群的机器
consul members;
2、查看集群主和从机器
consul operator raft list-peers
3、查看consul版本
[ec2-user@ccp-prod-k8m1 ~]$ consul version
Consul v1.12.3
Revision 2308c75e
Protocol 2 spoken by default, understands 2 to 3 (agent will automatically use protocol >2 when speaking to compatible agents)
如果按照原先的方式部署服务,会出现不稳定的情况;
2、自己手工注册服务
因为我们目前注册地址是 dbproxies;
我们可以看看这个机器的IP:
telnet dbproxies 8500
root@dev-fms-service-impl-prod-54fb8875d4-9gbsp:/logs# telnet dbproxies 8500
Trying 10.68.244.75...
Connected to dbproxies.ccp.svc.cluster.local.
Escape character is '^]'.
可以自己进入某个生产服务的pod 进行手工注册:
比如进入 ccp-gateway-bootstrap的生产的pod然后执行:
curl -s -X PUT -d '{"id":"yfq-acm-service-impl-8002-10-23-111-17-1174221935015174264","name":"2yfq-acm-service-impl","address":"172.20.187.129","port":9195,"tags":["yfq-faceservice"],"checks":[{"http":"http://10.23.111.17:8500/ui/","interval":"15s"}]}' http://dbproxies:8500/v1/agent/service/register
注意里面的check的path(10.23.111.17:8500) 一定要真实可用,否则服务注册会不成功;
然后看看 consul的服务是否正常
当然注册完了,
先使用命令看下:
curl dbproxies:8500/v1/agent/services
也可以查看缩略版本的:
curl dbproxies:8500/v1/catalog/services
也可以删除某个服务:比如acm-service-impl
curl -X PUT http://dbproxies:8500/v1/agent/service/deregister/a00-acm-service-impl-8002-10-23-111-17-7718219848784511644
不要着急,需要等一会儿才能注册上
在这里重启:
在ui里面看到服务又回来了:
如果注册不上需要进入pod看下日志:出现这个,说明注册成功
我发现删除有时候会失败,不着急,下面的两个方法都可以 先使用 接口 v1/agent/services查询一下,不稳定,有时候能查到,有时候查不到,多执行几次就可以了,等到查到了,然后执行删除的命令;
1、这样删除
curl -X PUT http://dbproxies:8500/v1/agent/service/deregister/a00-fms-service-impl-8012-172-20-123-22
2、这样删除
curl -X PUT http://10.23.111.17:8500/v1/agent/service/deregister/a00-fms-service-impl-8012-172-20-123-22
,
删除dbproxies注册的服务:
使用 10.68.244.75 可以把集群删掉;
curl -X PUT http://10.68.244.75:8500/v1/agent/service/deregister/test-acm-service-impl-8002-10-23-111-17-1
这样找到了自己注册的服务:
root@dev-acm-web-prod-dc6477dd6-5kmmm:/# telnet dbproxies 8500
Trying 10.68.244.75...
Connected to dbproxies.ccp.svc.cluster.local.
Escape character is '^]'.
curl 10.68.244.75:8500/v1/agent/services
4、可以查看详细的接口信息
在pod里面执行:
http://dbproxies:8500/v1/agent/services 详细信息
http://dbproxies:8500/v1/catalog/services -->这个是缩略的比较少,统计信息
5、正确删除姿势:
先查询:
curl dbproxies:8500/v1/agent/services
有时候是空的,有时候又有值;
等到查询到值的时候,执行:
curl -X PUT http://10.68.244.75:8500/v1/agent/service/deregister/a00-acm-service-impl-8002-dbproxies-3450823776658351514
就可以了: 如下图所示,刚开始 查询是空的,后来查询就有值了,然后执行删除就可以了;
6、查看健康状态,多执行几次,第一次可能是空的
参考:https://blog.csdn.net/u010173095/article/details/88569651
curl -X GET http://dbproxies:8500/v1/agent/checks
ttl健康检查有问题:https://www.cnblogs.com/duanxz/p/9662862.html
预发上面 也没有ttl健康检查;
通过比对自己注册的服务和当前生产注册的服务发现一个问题,生产注册的服务类型是ttl,但是手动注册的服务类型是http,ttl一直有问题,但是http却很正常;
例如:
生产注册的:
自己手动注册的:
问题很明显了,我们的使用了ttl模式注册有问题,但是使用http模式却没问题;
所以我们们首先要搞清楚 ttl和http模式到底是什么健康检查,是怎么执行的
参考文件:
Consul之:服务健康监测 - duanxz - 博客园
和https://juejin.cn/post/6878443985703010312
里面写的很清楚,consul的健康检查分为四个类型:
Check必须是Script、HTTP、TCP、TTL四种类型中的一种
但是我们使用了 springCloudConsul所以目前有两种类型:
1、http +interval
2、ttl类型(Time To live)
里面写的很清楚了,当spring.cloud.consul.discovery.heartbeat.enabled=true 代表使用ttl类型
如果为false代表为http+interval类型;
如果我们使用了ttl类型则要提供 一个定时任务schedule 定时上报到一个url上面,提供 ttl时间
spring.cloud.consul.host=122.8.189.23
#spring.cloud.consul.host=94.74.64.71
#spring.cloud.consul.host=94.74.68.42
spring.cloud.consul.service-registry.auto-registration.enabled=true
spring.cloud.consul.port=8500
spring.cloud.consul.discovery.health-check-critical-timeout=30s
spring.cloud.consul.discovery.heartbeat.enabled=true
spring.cloud.consul.discovery.heartbeat.ttl=10
spring.cloud.consul.discovery.enabled=true
spring.cloud.consul.discovery.register=true
spring.cloud.consul.discovery.port=${server.port}
spring.cloud.consul.discovery.preferIpAddress=true
spring.cloud.consul.discovery.instance-id=${cn.sunline.kite.instanceId}
spring.cloud.consul.discovery.metadata.dcn=${cn.sunline.kite.dcn}
spring.cloud.consul.discovery.metadata.artifactId=${cn.sunline.kite.artifactId}
spring.cloud.consul.discovery.metadata.gourpId=${cn.sunline.kite.groupId}
spring.cloud.consul.discovery.tags=${spring.profiles.active}
spring.cloud.consul.discovery.default-query-tag=${spring.profiles.active}
上面这是我们目前的配置;
当我们使用spring.cloud.consul.discovery.enabled=true的时候代表使用了ttl模式,
则spring.cloud.consul.discovery.heartbeat.ttl=10 这个参数会生效;其他参数自动变成空;
当spring.cloud.consul.discovery.enabled=false的时候代表使用了http模式,
spring.cloud.consul.discovery.heartbeat.ttl 你无论填上什么值,在追踪日志的时候都是空;
然后会使用:
spring.cloud.consul.discovery.health-check-interval =10(可以新增这个变量)
spring.cloud.consul.discovery.health-check-path = /actuator/health(可以新增这个变量)
我上面写的是默认值,也就是说如果你不添加这两个变量,会默认走这两个值;
###consul###
spring.cloud.consul.host=10.10.200.15
spring.cloud.consul.service-registry.auto-registration.enabled=true
spring.cloud.consul.port=8500
#定义 consul 健康检查路径
spring.cloud.consul.discovery.health-check-path=/actuator/health
# # 执行监控检查的频率
spring.cloud.consul.discovery.health-check-interval=10s
spring.cloud.consul.discovery.health-check-critical-timeout=30s
spring.cloud.consul.discovery.heartbeat.enabled=true
spring.cloud.consul.discovery.heartbeat.ttl=10
spring.cloud.consul.discovery.enabled=true
spring.cloud.consul.discovery.register=true
spring.cloud.consul.discovery.port=${server.port}
spring.cloud.consul.discovery.preferIpAddress=true
spring.cloud.consul.discovery.instance-id=${cn.sunline.kite.instanceId}
spring.cloud.consul.discovery.metadata.dcn=${cn.sunline.kite.dcn}
spring.cloud.consul.discovery.metadata.artifactId=${cn.sunline.kite.artifactId}
spring.cloud.consul.discovery.metadata.gourpId=${cn.sunline.kite.groupId}
spring.cloud.consul.discovery.tags=${spring.profiles.active}
spring.cloud.consul.discovery.default-query-tag=${spring.profiles.active}
###consul###
可以查看日志(acm-service-impl的):
(a)这是http模式的日志:注意http模式即使你配置了ttl也是空;
[2022-08-29 09:36:46:932] [INFO ] [main] [ConsulServiceRegistry] Registering
service with consul: NewService{id='a00-acm-service-impl-8002-dbproxies-1853363605372601210',
name='a00-acm-service-impl', tags=[nova], address='172.20.26.165',
meta={dcn=a00, artifactId=acm-service-impl, gourpId=cn.sunline.acm, secure=false}, port=8002,
enableTagOverride=null, check=Check{script='null', dockerContainerID='null',
shell='null', interval='10s', ttl='null', http='http://172.20.26.165:8002/actuator/health',
method='null', header={}, tcp='null', timeout='null', deregisterCriticalServiceAfter='30s', t
lsSkipVerify=null, status='null', grpc='null', grpcUseTLS=null}, checks=null}
(b) 这是ttl模式的日志:注意ttl这时候已经生效了;
结论
改动很简单,直接将
spring.cloud.consul.discovery.heartbeat.enabled=false
也就是 从ttl模式改到 http模式就可以了;
他们的区别是:
ttl模式是 提供一个定时任务,主动上传到consul的接口,是推的模式;
http模式 是提供一个监控检查的url, consul主动去轮训检查,是拉的模式;
你在执行 dbproxies:8500/v1/agent/checks的时候,会发现;生产 有这个ttl和http的问题,
但是预发没有这个问题,预发这个type是空的,因为预发是单机部署,不存在这个问题;
标签:服务,
spring,
Consul,
往下掉,
ttl,
http,
consul,
cloud,
discovery
From: https://www.cnblogs.com/aspirant/p/16639404.html