k3s原理分析丨如何搞定k3s node注册失败问题
前 言
面向边缘的轻量级K8S发行版k3s于去年2月底发布后,备受关注,在发布后的10个月时间里,Github Star达11,000颗。于去年11月中旬已经GA。但正如你所知,没有一个产品是十全十美的,k3s在客户落地实践的过程中也暴露过一些不足。在k3s技术团队的专业技术支持下,许多问题得到了改善和解决。
我们精选了一些在实际生产环境中的问题处理案例,分享给正在使用k3s的你。希望k3s技术团队的经验能够为你带来参考,也希望你可以参与进来和我们一起探索切磋。毕竟,寻找答案的路途永远没有终点。
本文将分享k3s产品中关于node注册失败的排查记录。
排查记录
问题描述
k3s版本:v1.17.2+k3s1
k3s agent向server注册时,日志出现明显报错:

同时,在k3s server上查询node,也确实无法获取注册的节点信息(只有一个server节点):

客户的虚拟机环境使用某私有云,从反馈看有过VM反复清理的操作,不过具体操作无法完整复原。
基本原理
Agent注册的过程是十分复杂的,总的来说有两个目的:
启动kubelet等服务,连接到server节点上的api-server服务,这是k8s集群必须的
建立websocket tunnel,用于k3s的server和agent同步一些信息
我们在注册agent时只提供了server地址和node-token,agent是如何一步一步完成注册的?首先看node-token的格式:

这里的user和password会对应k3s api-server中basic auth的配置,k3s api-server启动时会设置一个特殊的authentication方式就是basic auth,对应文件在server节点的/var/lib/rancher/k3s/server/cred/passwd中:
1a51f67d17af05b6f48357f46a9c6833,server,server,k3s:server
0050004354d29b565f4a8bf2faba769e,admin,admin,system:masters
1a51f67d17af05b6f48357f46a9c6833,node,node,k3s:agent
由此agent端通过解析node-token,可以获得一个和k3s api-server通信的授权,授权方式是basic auth。
了解node-token的作用,我们就可以解开agent注册过程的序幕,参考下图:

以黄色文本框顺序为例,前三步是为了得到启动kubelet服务各种依赖信息,最后一步建立websocket通道。我们可以只关心前面三步,最重要的是api-server的地址,还有各种k8s组件通信的tls证书,由于那些证书是在server上签发,所以agent需要通过一些API请求获取,这些证书大致有:
/v1-k3s/serving-kubelet.crt
/v1-k3s/client-kubelet.crt
/v1-k3s/client-kube-proxy.crt
/v1-k3s/client-k3s-controller.crt
/v1-k3s/client-ca.crt
/v1-k3s/server-ca.crt
...
这些证书中kubelet两个证书最为特殊,由于kubelet在每个节点都运行,所以安全需要我们需要给每个kubelet node都单独签发证书(node-name作为签发依据)。涉及到单独签发就需要验证node信息是否合法,这时node-passwd就粉墨登场了。
这个过程大致是这样的,agent先生成一个随机passwd(/etc/rancher/node/password),并把node-name和node-passwd信息作为证书请求的request header发给k3s server,由于agent会向server申请两个kubelet证书,所以会收到两个带有此header的请求。如果agent首次注册,server收到第一个请求后,会把这个node-name和node-passwd解析出来存储到/var/lib/rancher/k3s/server/cred/node-passwd中,收到第二个请求后会读取node-passwd文件与header信息校验,信息不一致则会403拒绝请求。如果agent重复注册时,server会直接比对request header内容和本地信息,信息不一致也会403拒绝请求。
原因分析
了解基本原理后,我们再回到问题本身,agent在注册时报出的错误日志如下:
level=error msg="Node password rejected, duplicate hostname or contents of '/etc/rancher/node/password' may not match server nod
e-passwd entry, try enabling a unique node name with the --with-node-id flag"
查找代码出处,确实发现这是在申请kubelet证书时,k3s server返回的403导致的:

对比agent上的node-passwd(/etc/rancher/node/password)和server上的node-paswd:
# agent
$ cat /etc/rancher/node/password
47211f28f469622cccf893071dbda698
$ hostname
xxxxxxx
# server
cat /var/lib/rancher/k3s/server/cred/node-passwd
31567be88e5408a31cbd036fc9b37975,ip-172-31-13-54,ip-172-31-13-54,
cf3f4f37042c05c631e07b0c0abc528f,xxxxx,xxxxxx,
Agent node对应的passwd和server中存储的hostname对应的passwd不一致,按照我们前面说的基本原理,就会出现403的错误日志。
解决方案
为什么会出现passwd不一致呢?正常来说如果用k3s-agent-uninstall.sh来清理安装过的agent node,并不会删除password文件(/etc/rancher/node/password),那么问题很可能是VM重建或者手动操作删除的这个文件。因为agent上删除了password,agent再次注册时会重新生成password,就导致了新的password和server上原先存储的不一致。
解决办法可以有三种:
手动在agent上创建password,内容和server中存储保持一致
修改了server中的原始内容,让password和agent上新生成的保持一致
可以试试agent注册时使用--with-node-id,这样server中认为这完全是新node,不会用原始信息比对
总 结
原则上不建议用户去触碰文中提到的这些文件,尽量把控制权交给k3s,即使我们清理agent节点,也尽量利用k3s内置的脚本。如果碰到此类问题,可以参考本文的原理介绍去分析,并通过已知的解决方案去修复它。
k3s原理分析丨如何搞定k3s node注册失败问题的更多相关文章
- LSV又新增13个地质图!量测对比分析全都能搞定
对于地质工作者来说,地质图是个十分重要的参考资料.随着国家解密的地质资料越来越多,能够有效的把各种地质资料结合起来,进而提高地质工作者的作业效率,是十分有意义的. LSV(LocaSpaceViewe ...
- 一文搞定全场景K3s离线安装
作者简介 王海龙,Rancher中国社区技术经理,负责Rancher中国技术社区的维护和运营.拥有6年的云计算领域经验,经历了OpenStack到Kubernetes的技术变革,无论底层操作系统Lin ...
- 夯实Java基础系列3:一文搞懂String常见面试题,从基础到实战,更有原理分析和源码解析!
目录 目录 string基础 Java String 类 创建字符串 StringDemo.java 文件代码: String基本用法 创建String对象的常用方法 String中常用的方法,用法如 ...
- ASP.NET MVC中分析淘宝网页发生乱码标题搞定方法
ASP.NET MVC中分析淘宝网页发生乱码标题搞定方法 近来正在分析淘宝中商品的信息,效果发生乱码,如: 原因便是中文字符格式发生冲突,ASP.NET MVC 默认采用utf-8,可是淘宝网页采用g ...
- 一文搞定 SonarQube 接入 C#(.NET) 代码质量分析
1. 前言 C#语言接入Sonar代码静态扫描相较于Java.Python来说,相对麻烦一些.Sonar检测C#代码时需要预先编译,而且C#代码必须用MSbuid进行编译,如果需要使用SonarQub ...
- 100天搞定机器学习|Day56 随机森林工作原理及调参实战(信用卡欺诈预测)
本文是对100天搞定机器学习|Day33-34 随机森林的补充 前文对随机森林的概念.工作原理.使用方法做了简单介绍,并提供了分类和回归的实例. 本期我们重点讲一下: 1.集成学习.Bagging和随 ...
- 2021升级版微服务教程6—Ribbon使用+原理+整合Nacos权重+实战优化 一篇搞定
2021升级版SpringCloud教程从入门到实战精通「H版&alibaba&链路追踪&日志&事务&锁」 教程全目录「含视频」:https://gitee.c ...
- 100天搞定机器学习|Day8 逻辑回归的数学原理
机器学习100天|Day1数据预处理 100天搞定机器学习|Day2简单线性回归分析 100天搞定机器学习|Day3多元线性回归 100天搞定机器学习|Day4-6 逻辑回归 100天搞定机器学习|D ...
- oracle分页查询及原理分析(总结)
oracle分页查询及原理分析(总结) oracle分页查询是开发总为常用的语句之一,一般情况下公司框架会提供只需套用,对于增删改查而言,查是其中最为关键也是最为难的一块,其中就有使用率最高的分页查询 ...
随机推荐
- idea 连接mysql报错:Access denied for user 'root'@'localhost'(using password:YES)。
这两天在idea中开发Web项目时,连接MYSQL数据库,出现问题:Access denied for user 'root'@'localhost'(using password:YES). ...
- 使用VMware vSphere Client管理ESXI(新建虚拟机)
1.下载vSphere Client客户端 2.将镜像文件(ISO)上传到ESXI主机,具体操作见如下链接地址 https://blog.csdn.net/amandazhouzhou/article ...
- VirtualBox端口映射
问题:VirtualBox里面启动Django项目后发现在虚拟机能打开,在物理机上无法打开如图: 解决方法:端口映射 问题解决!其他端口问题只需要添加对应端口即可,比如xshell连接虚拟机要添加22 ...
- [Usaco2009 Oct]Heat Wave 热浪(裸最短路径)
链接:https://ac.nowcoder.com/acm/contest/1082/F来源:牛客网 题目描述 The good folks in Texas are having a heatwa ...
- 吴裕雄--天生自然python学习笔记:python 用pygame模块制作一个音效播放器
用 Sound 对象制作一个音效播放器. 应用程序总览 程序在执行后默认会把 WAV 音频文件加载到清单中,单击“播放”按钮可开始 播放,同时显示 “正在播放 xxx 音效”的信息 . 播放过程中,可 ...
- js使用心得——避免全局变量冲突的小技巧
在写js代码的时候,经常会因为这样或者那样的原因用到全局变量,如果全局变量只在一个js里使用,那就没问题,但如果变量在不同的js文件里出现,这时隐藏的问题就会开始暴露,也许你能很快修复出现的BUG,又 ...
- java5的静态导入import static
在Java 5中,import语句得到了增强,以便提供甚至更加强大的减少击键次数功能,虽然一些人争议说这是以可读性为代价的.这种新的特性成为静态导入. 1.静态导入的与普通import的区别: imp ...
- linux下使用过的命令总结(未整理完)
1.常用命令不需解释 ls\cd\cp\mv\pwd\file\vi\vim\cat 2.getconf LONG_BIT 终端返回32表示操作系统32位,返回64表示操作系统64位. 3.ifcon ...
- MOOC(7)- case依赖、读取json配置文件进行多个接口请求-执行测试用例(16)
执行测试用例 # -*- coding: utf-8 -*- # @Time : 2020/2/12 22:56 # @File : run_test_16.py # @Author: Hero Li ...
- LeetCode Day 2
LeetCode0004 给定两个大小为 m 和 n 的有序数组 nums1 和 nums2. 请你找出这两个有序数组的中位数,并且要求算法的时间复杂度为 O(log(m + n)). 你可以假设 n ...