vmware 搭建k8s无法ping通子节点_一波四折 —— 记一次K8S集群应用故障排查

2023-11-05

5d77e664d458388a9bbb5e4f332d14b3.gif f8d5bfbb01a578ba16595206a43c52f9.png一波四折 5d77e664d458388a9bbb5e4f332d14b3.gif ——记一次K8S集群应用故障排查 446ef5d5f03849b4e68407f31a1202c4.png Part1 初露端倪 eba7e0a1d1246ed48f0cbe6436e54f34.png 64dd880342ce5bac814daf7dab57a810.gif

一个周四的下午,客户的报障打破了微信群的平静。

“我们部署在自建K8S集群上的应用突然无法正常访问了,现在业务受到了影响!”

收到客户的报障,我们立刻响应,向客户了解了问题现象和具体报错信息。

客户反馈K8S集群部署在云主机上,K8S的应用pod example-app通过访问外部域名example-api.com调用接口,同时访问云数据库做数据查询后将结果返回客户端。客户排查应用pod日志,日志中有如下报错:

ee860c5f1fbb41c832378364e9a292d0.png

可以看到最关键的信息是Name or service not known。该报错一般为域名无法解析导致的。

由于客户的应用pod只访问example-api.com这一个外部域名,因此判断应该是pod解析该域名时出现异常。为了进一步验证,我们执行kubectl exec -it example-app /bin/sh命令进入pod内执行ping example-api.com命令,果然出现了相同的报错。

ea0742bd3aae2ea2679756f8e41cd74e.png

因此可以确认应用日志中的报错是域名解析失败导致的。

执行kubectl get pod example-app -o yaml|grep dnsPolicy查看pod的dns策略,是ClusterFirst模式,也就是pod使用K8S集群的kube-dns服务做域名解析。

执行命令kubectl get svc kube-dns -n kube-system,确认kube-dns服务的clusterIP是192.168.0.10 查看pod内的/etc/resolv.conf文件,nameserver设置的正是该IP。再执行kubectl describe svc kube-dns -n kube-system|grep Endpoints,可以看到dns服务关联了一个coredns pod作为后端。

执行kubectl get pods -n kube-system|grep coredns看到kube-dns关联的coredns pod处于running状态。

再执行kubectl logs coredns –n kube-system,看到pod日志中有大量和客户配置的外部dns服务器IP地址通讯超时的报错。

1fbea157373c7fec3a7e2efa13d8ce7e.png

10.16.16.16和172.16.16.16为客户自建DNS服务器的IP地址

。为了确认是否是DNS服务器有问题,我们在example-app pod中分别执行nslookup example-api.com 10.16.16.16和nslookup example-api.com 172.16.16.16,均能解析出正确的IP地址。

因此判断问题应该出在coredns pod上。此时我们发现,coredns pod的状态变成了crashloobbackoff,稍后又变成了running。

观察一段时间后发现pod在这两个状态之间反复切换。鉴于整个集群只有一个coredns pod,我们修改了coredns的deploy,将pod副本数调至2,新扩的pod一直处于running状态,pod日志中也没有出现和10.16.16.16、172.16.16.16的通信超时的报错。而此时example-app pod也可以正常解析域名了!可以确认之前是集群唯一的coredns pod状态异常导致集群DNS服务不可用。

那么coredns pod为什么会出现异常呢?

再次查看异常的pod日志,发现除了和外部DNS服务器有通讯超时的记录,还有和集群api-server通讯超时的记录。因此有必要怀疑是pod所处的网络有问题。在客户的K8S集群网络规划中,pod使用和集群node不同的子网通讯。通过在K8S节点云主机上绑定pod子网的弹性网卡,在网卡上给节点的pod在pod子网中分配IP,实现pod的网络可达。

由于example-app pod是可以与外部通讯的,因此pod子网层面是没有问题的。我们将焦点移至coredns pod使用的弹性网卡上。弹性网卡在节点云主机操作系统中的设备名是eth1,pod子网网关是10.176.96.1在节点上执行ping -I eth1 10.176.96.1,结果如图:

1d0e8a08e2e223bcc5bd651687d8e230.png

可见云主机无法通过eth1 ping通子网网关,而且找不到eth1设备。执行ifconfig命令发现eth1设备没有被系统识别到。而弹性网卡底层是被正常挂载到云主机上的。

手动执行echo 1 > /sys/bus/pci/rescan命令重新扫描弹性网卡,发现eth1出现了,此时执行ping -I eth1 10.176.96.1也可以ping通了!而异常的coredns pod也恢复了正常。判断之前应该是系统异常导致的网卡没有被识别到导致。

通过这一问题也提醒我们如果集群需要使用kube-dns服务,coredns的pod一定要配置多副本,以免单个pod异常导致集群DNS不可用。

446ef5d5f03849b4e68407f31a1202c4.png Part2 一波刚平一波又起 eba7e0a1d1246ed48f0cbe6436e54f34.png 64dd880342ce5bac814daf7dab57a810.gif

域名解析的问题解决,本以为已经结案,谁知新的问题接踵而来。客户调用应用,不再报错域名解析失败。但是仍然不能正常返回结果。排查应用日志,报错如下:

eb74864bf1b6c0dae5f3fb9ac3b37b4e.png

通过报错判断是应用pod连接云数据库超时导致。排查云数据库所在子网的路由、ACL和白名单设置,均无异常。连接pod后可以ping通数据库域名,判断pod与数据库的网络链路是正常的。但是pod内无法telnet通数据库域名的3306端口,判断这就是导致连接数据库超时的原因了!

排查pod内的防火墙,没有开启。pod所在的子网ACL,没有限制。表面的分析没有任何线索,于是只能祭出网络问题排查的经典手段——tcpdump抓包!

由于pod内的容器一般CPU、内存、网络资源和存储空间有限,在pod内抓包会占用大量资源和存储空间,抓包结束后数据包取出也比较繁琐。而且有的容器镜像是无法安装tcpdump工具的。所以通常我们不会在容器内抓包。

基于K8S集群的网络架构,pod的网络通讯是通过所在节点云主机的辅助弹性网卡收发数据的。因此我们只要在pod所在节点云主机上对相应的网卡进行抓包即可。

在客户的场景下,应用pod使用所在节点的eth1网卡,所以pod telnet云数据库的3306端口时,我们直接在节点上抓取eth1网卡上与云数据库IP交互的数据包即可。

pod的IP是10.176.98.29,云数据库的IP是10.176.46.4。在pod的容器内执行telnet 10.176.46.4 3306,同时在节点上执行tcpdump -i eth1 host 10.176.46.4 -w /tmp/mysql.cap。pod内telnet超时后,我们结束抓包,将cap文件取出后发现居然一片空白,一个包都没有抓到!

这不科学!

之前pod内可以ping通云数据库,说明一定有数据包从pod所在云主机发出并收到了回包。为了验证pod telnet请求的包是否正常发出,我们干脆不把抓包范围局限在eth1网卡,而是使用tcpdump -i any host 10.176.46.4 -w /tmp/mysql.cap对云主机所有网络接口抓包。这次终于抓到了数据包,发现telnet发出后,没有收到数据库的任何回包。

bcc7a56671a0e56b08813c79284477e8.png

在telnet的同时,集群中有其他pod可以正常连接云数据库,所以因为云数据库侧异常导致没有回包的可能性不大。云主机可以和外界通讯的网卡只有eth0和eth1,莫非……为了验证我们的猜想,在telnet时,节点上执行tcpdump -i eth0 host 10.176.46.4,果然看到了pod发出的到云数据库的数据包!

af052e2de32c44b18b973ad310699ccc.png

所以pod 容器telnet不通云数据库3306端口的原因也真相大白了。因为pod telnet云数据库的数据包没有走eth1,而是走了eth0,数据包发送至云数据库后,云数据库的回包发给了pod的子网网关。

SDN网络OVS判断来包是从node子网网关发出(eth0),而回包却是发往pod子网(eth1)源和目的地址不一致,因此将数据包丢弃。pod也就无法收到数据库的回包了。之前可以ping通是因为ICMP协议是代答的,即使源和目的地址不一致,也可以正常收到回包。

那么,pod的所有网络请求正常是应该通过云主机上的辅助网卡收发的,为什么走了云主机主网卡了呢?正常的K8S集群节点上配置了table 2路由规则,定义了pod的网络请求默认路由的下一跳是pod子网网关,并且走辅助网卡,如下图所示:

71eb2a69b6bd34fe51a4fedb57390fa3.png

而在客户的应用pod所在节点执行ip r show table 2,我们看到的结果和第一次抓包一样,空空如也。。。

路由是由K8S集群的网络插件维护,路由缺失问题在网络插件日志中没有发现任何线索,具体原因不得而知。当务之急是修复问题。

可以通过重启ipamd容器恢复table 2路由。

执行docker ps | grep ipamd | grep sh找到ipamd的容器ID。

然后执行docker restart 容器ID重启容器。

再次执行ip r show table 2,终于看到了路由规则!

Finally,此时在应用pod内测试可以telnet通云数据库的3306端口。客户的应用调用也终于可以成功返回结果。

然鹅,如果各位看官觉得这个case到这里就结束了,那就和当时排障的攻城狮一样图样图森破了。

446ef5d5f03849b4e68407f31a1202c4.png Part3

慢=不可用

64dd880342ce5bac814daf7dab57a810.gif

就在攻城狮以为一切都恢复正常时,客户的追加反馈表明这个问题只是进入了下一个阶段。

客户反馈应用虽然可以正常调用,但是一次调用要超过一分钟才能有返回结果,之前正常的速度是仅需几秒就可以返回结果。现在这样的速度完全不能满足业务要求,相当于还是不可用的。

问题尚未解决,攻城狮仍需努力!

分析应用调用返回慢的问题,一是着眼于应用流程的各个环节,如客户端,服务端对业务请求的处理时间,另外一个就是排查数据传输链路是否有延迟。在客户的场景下,就是确认pod和云数据库在处理请求上是否有瓶颈,还有就是pod到云数据库之间的网络传输是否有延迟。在pod内ping云数据库IP,没有超时丢包,延迟很低。

b9c75a400bef1875e429d557f08056c2.png

要想确认pod和云数据库在处理请求时的时长,还是要依靠tcpdump工具抓包分析。于是我们在pod对数据库发起一次完整的请求过程中,依然使用tcpdump -i eth1 host 10.176.46.4 -w /tmp/mysql.cap命令在pod所在节点抓包。将数据包取出后分析发现,一次完整的业务请求,pod会对数据库做13次查询。对比第一次查询和最后一次查询的时间,如图所示:

1ddf0436527554d9cd2eab78c57156a4.png

可以发现13次请求用了1分钟左右,与业务调用耗时吻合。排查云数据库监控,发现内存

使用接近100%

4b3264813aec506c0b45aef7bdb1ce38.png

同时实例慢查询日志中有大量慢sql记录,可以看到几乎每次查询都耗时较长

64c69a811499a2910bd94d44a35d1782.png

可见如果业务调用的13次请求,每次都是慢查询,耗时4秒左右,就会导致我们看到的完整请求耗时一分钟左右。

因此判断瓶颈应该主要在云数据库上,建议客户对数据库慢查询进行优化,降低内存负载。然后观察应用调用时长是否恢复正常。

446ef5d5f03849b4e68407f31a1202c4.png

part4 问题的真相只有一个!

64dd880342ce5bac814daf7dab57a810.gif

当我们天真地以为优化完数据库慢查询后,一切就都尘埃落定时。客户的反馈几乎让人崩溃——优化慢查询后,数据库内存使用已降至30%,慢日志中也几乎没有慢sql记录。而应用的调用时长仍然没有缩短!

一定还有哪个环节有疏漏。

为了完整了解应用pod在应用调用过程中都产生了哪些数据交互,我们决定再次抓包分析,但焦点不再集中在云数据库上,而是以pod维度进行抓包。使用tcpdump -i eth1 host -w /tmp/app.cap命令在pod所在节点抓取所有和pod相关的包,分析数据包后果然有了新的发现:pod与100.64.249.132这个地址有文件传输交互。

224f826920ed588d3d2ff88c1d69eaea.png

查看数据包详细数据发现这个地址是OSS对象存储解析到的域名!pod还会与oss传输文件这个重要环节在此前是不知道的,客户也没有主动告知。

这也提醒我们在分析应用问题时,务必要搞清完整的业务调用流程,应用架构和涉及到的产品环节,否则挤牙膏似的信息输出和被问题现象牵着鼻子走,会浪费大量时间,甚至严重阻碍问题排查。

我们在pod内测试ping 100.64.249.132,延时非常感人。

ab5a8999f54b00c1d42bea89c61b8634.png

与客户确认,客户反馈OSS域名解析的IP貌似不对。在业务架构规划时,为了保证客户pod与oss的网络性能,配置了通过专线连接oss。当前解析的IP没有走专线网段,而是走了普通的网段,无法满足性能要求。正常走专线的域名解析IP应该是10.219.226.2。

但是域名解析为什么会出现问题呢?

各位童鞋是否还记得part1中我们提到客户的pod使用的是kube-dns提供的dns解析,而kube-dns配置的上游服务器是客户自建的dns服务器?经过客户测试发现,自建dns服务器对oss域名的解析就是100.64.249.132。应该是近期客户侧维护dns服务器的时候误操作修改了解析导致的。。。将自建dns服务器的域名解析地址修改回正确地址后。再次在pod内测试,结果如下:

821dddb3c2b3d152e1734e0f844a5e77.png

再次测试应用调用,终于恢复到了正常的时长!可喜可贺!

7a35d7ac9c059dbc36d68d55949b2e94.gif

 至此客户的问题卍解,总结问题排查过程,有几点值得分享:

1、  k8s集群如果使用kube-dns服务,coredns pod务必配置多副本,避免单点故障导致集群dns服务不可用。

2、  排查K8S集群pod网络问题时,可以在pod所在节点抓取pod使用的辅助网卡的相应网络数据包,避免直接在pod内抓包。

3、  应用系统性能排查涉及到各个节点设备和网络传输,务必了解清楚完整的系统架构,调用流程,再针对涉及的每个环节逐一分析。

7a35d7ac9c059dbc36d68d55949b2e94.gif

以上就是一次“波折”的K8S应用问题排查过程,感谢各位童鞋阅读,如果能够对大家有所帮助,欢迎点赞转发评论。关注我们的公众号,更多精彩内容会持续放送!

a01b48eb4a17e78123dac3a6b26e3146.png

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

vmware 搭建k8s无法ping通子节点_一波四折 —— 记一次K8S集群应用故障排查 的相关文章

随机推荐

  • 2019年个人总结

    今天是今年的最后 一天 写个个人总结 对自己一年来的工作进行总结 通过分析和研究进而肯定成绩并找出问题 得出经验和教训 2019年自己的前端方面 移动端 完成了好艺的app项目 协会的微官网 好艺的app转为公众号 学生开学统计项目等 其中
  • Python10个与数学有关的简单实例代码

    注意 我用的python2 7 大家如果用Python3 0以上的版本 请记得在print 函数哦 如果因为版本问题评论的 不做回复哦 1 题目 有1 2 3 4个数字 能组成多少个互不相同且无重复数字的三位数 都是多少 程序分析 可填在百
  • Javascript之BOM与DOM讲解

    文章转载自 https blog csdn net qq877507054 article details 51395830 一 Javascript组成 JavaScript的实现包括以下3个部分 ECMAScript 核心 描述了JS的
  • 项目开发中常用的十六进制方式打印实现

    在项目开发中 比如网络开发 多媒体播放开发等 常常用到将接受数据和发送数据或者需要解析的数据 用打印方式呈现 方便自己定位问题 在这个时候 printf难免没有满足我们的需要了 因为printf bufdata s n bufdata 是用
  • keil Error: Could not load file解决方法

    1 你点完建造文件 然后进行调试 不会出错 2 不要点编译文件 编译后文件调试状态关闭了 再调试 这样就会出这个错误
  • js-基础知识(一)

    1 在html中引入js的两种方法 1 页面内嵌 2 外部引入 为符合web标准 w3c标准中的一项 结构 样式 行为相分离 通常会采用外部引入
  • mmsegment数据pipeline操作(七)

    目录 1 数据项配置 2 voc数据集传入参数 3 CustomDataset数据读取 4 self pipeline results 4 1 读图 4 2 数据增广 4 3 格式转换 4 4 测试 5 扩展和使用自定义管道 1 数据项配置
  • 计算机专业留学动机信范文,出国留学,如何写好动机信(Motivation Letter)?

    一篇好的动机信最重要的是简洁易懂 用最简洁的语言展示申请者最突出的优点 浙大毕业后在美国 UIUC 和欧洲 KTH CTH EPFL NTNU 留学 PhD 另外由于在之前的工作中也参与系里招生 帮老板评审申请材料 参与系里招生会议 经手的
  • 数据结构之线性表预习

    1 简述线性表中顺序存储结构的含义及主要元素 描述顺序存储结构需要三个属性 1 存储空间的起始位置 数组 data 它的存储位置就是存储空间的存储位置 2 线性表的最大存储容量 3 线性表的当前长度 数组长度 与 线性表长度区别 数组长度
  • 编程新手导论

    第二部分 导论 这一部分主要是关于编程的导论 要懂得一点思想具备一点常识 设计 编码 与软工 编程与思想 这一章解释了三种思想 原语 抽象 组合 和软件开发的二个重要过程 软件工程的相关概念 是编程入门的关键 要懂得一点领域内的数学 数学与
  • python3读取图片并灰度化图片的四种方法(OpenCV、PIL.Image、TensorFlow方法)总结

    在处理图像的时候经常是读取图片以后把图片转换为灰度图 作为一个刚入坑的小白 我在这篇博客记录了四种处理的方法 首先导入包 import numpy as np import cv2 import tensorflow as tf from
  • 【网络】IP协议相关的技术(DNS、ARP、ICMP、DHCP)简析

    1 DNS 域名解析协议 TCP IP中使用IP地址和端口号来确定网络上的一台主机的一个程序 但是IP地址不方便记忆 于是人们发明了一种叫主机名的东西 是一个字符串 并且使用hosts文件来描述主机名和IP地址的关系 DNS协议是将域名转换
  • COCO和VOC数据集的转换:VOC2COCO和COCO2VOC

    VOC2COCO 方法一 参考自博客 数据格式的转换实际是将VOC的annotation标注文件转化为COCO的json文件 注 下面代码包含通过txt文件生成和通过文件夹生成两种方法 1 通过txt文件生成 按照VOC数据集下ImageS
  • 海康RTSP客户端连接深入分析

    海康相机RTSP连接代码分析 最近在做海康相机rtsp连接获取音视频的工作 现在介绍一下分析过程和源码 源码在我上传的共享资料中 http download csdn net detail zhouyongku 8203521 一 基本原理
  • AHB2APB桥接器设计(1)——基本原理

    点击进入 硬件安全 社区 查看更多精彩内容 点击查看 AMBA总线 系列文章 声明 作者主页 摆渡沧桑的CSDN主页 未经作者允许 禁止转载 本文为非盈利性质 目的为个人学习记录及知识分享 因能力受限 存在知识点分析不正确的可能 若您参考本
  • 模拟地与数字地详解

    二者本质是一直的 就是数字地和模拟地都是地 要明白为什么要分开 先听一个故事 我们公司的商务楼 2楼是搞模拟的 3楼是搞数字的 整幢楼只有一部电梯 平时人少的时候还好办 上2楼上3楼互不影响 但每天上下班的时候就不得了了 人多得很 搞数字的
  • SpringBoot打包报错Failed to execute goal org.springframework.boot:spring-boot-maven-plugin:2.1.4.RELEASE

    当不希望将SpringBoot打包成独立运行的jar 而只是当做工具jar包时 去掉启动类 打包报错 Failed to execute goal org springframework boot spring boot maven plu
  • alibaba/druid 常见问题

    1 363 Fork895 renfufei edited this page on 16 Sep 2014 51 revisions Pages 54 Benchmark aliyun Contributors DBCP迁移 Druid
  • SpringBoot 启动连接Nacos:[NACOS ConnectException httpPost] currentServerAddr: http://localhost:8848

    错误信息 2022 06 12 21 20 20 383 ERROR 33840 localhost 8848 c a n c config http ServerHttpAgent NACOS ConnectException httpP
  • vmware 搭建k8s无法ping通子节点_一波四折 —— 记一次K8S集群应用故障排查

    一波四折 记一次K8S集群应用故障排查 Part1 初露端倪 一个周四的下午 客户的报障打破了微信群的平静 我们部署在自建K8S集群上的应用突然无法正常访问了 现在业务受到了影响 收到客户的报障 我们立刻响应 向客户了解了问题现象和具体报错