上个月我刚给一套线上Hadoop集群做过扩容,新到的那批机器预装的全是银河麒麟V10,而老集群清一色CentOS 7.9,管理工具是Ambari 2.7.x。'CentOS老集群 + 麒麟新节点'这套组合,比同版本扩容麻烦得多。光是把节点注册进去、装上Ambari Agent这一步,就可能卡你半天。这篇东西就是把整个流程拆开揉碎讲清楚:麒麟节点怎么初始化、Ambari Agent怎么装、注册时哪些检查会拦你、服务部署阶段会踩哪些坑。适合正在做国产化系统迁移的运维同学,也适合手里有一堆老CentOS集群、被迫往里面加新机器的数仓工程师参考。
1. 扩容前的思路与前置检查
1.1 先搞清楚你的Ambari和HDP版本底线
很多人上来就装Agent,装完了发现注册不上,然后到处查网络。我的习惯是:动手之前先把这个版本关系理清楚。Ambari本身只是个管理壳,真正干活的是HDP那套组件栈。Ambari 2.7.6配HDP 3.1.5是线上非常常见的组合,这套组合默认的host os是CentOS 7、RedHat 7这类RHEL 7系。你拿一个基于RHEL 8或更新内核的麒麟版本去注册,Ambari的OS兼容性检查会直接给你颜色看。
登录新节点后先跑这一组命令,把家底摸清楚:
cat /etc/os-release cat /etc/redhat-release uname -r python --version ldd --version麒麟V10有很多个SP版本,不同版本对RHEL的兼容基线不一样。有些偏RHEL 7,有些偏RHEL 8。这不是'所有麒麟都一样'能概括的。判断完系统版本之后,你要问自己三个问题:
第一,Ambari的stack定义里有没有Kylin的OS类型。如果Ambari Server上报的OS类型不在支持列表里,UI上注册主机的第一步就会把节点标红。第二,HDP组件rpm包的依赖在麒麟上能不能补齐,比如perl、openssl-devel、nc、python-devel这些基础包。第三,JDK路径能不能做到和全集群一致。Ambari对Java Home的管理是全局生效的,你老节点装在/usr/jdk64/jdk1.8.0_202,新节点上没有这个目录,后面部署DataNode的时候脚本直接炸。
1.2 节点基线检查,别省这一步
新机器拿到手,别急着塞机柜里装系统。先把硬件和系统层面的设计决定好。我之前接过一个扩容需求,机器到了才发现数据盘只有系统盘一块,后面做DataNode目录的时候只能重新挂盘,扩容窗口硬生生多花了半天。
建议按这个清单逐项核对:
- 主机名:确认和现有节点不重名。Hadoop集群主机名建议短横线风格,比如
kylin-dn-104,不要用大写、下划线。 - IP规划:提前把所有节点IP写进彼此的
/etc/hosts,包括Ambari Server、老节点、新节点。Ambari对主机名解析极其敏感,经常出现'host not found'就是这里漏了。 - 磁盘:DataNode节点建议数据盘独立挂载,不要和系统盘混在一起。文件系统建议XFS。确认磁盘盘符、分区表、挂载点设计完毕。
- 内存与CPU:和现有节点规格尽量保持一致,不一致也要在Ambari部署时单独调整DataNode/NodeManager的堆内存,否则集群里出现'小马拉大车'的节点会拖慢整个集群。
- 网络:检查网卡是否全部UP、多网卡环境要确定Ambari Agent上报哪个IP,别让心跳走了一条千兆管理口,数据流量全怼到万兆业务口。
# 快速检查命令 ip addr df -h free -h nproc cat /etc/hosts做这轮检查的核心目的只有一条:把环境变量控制住,后面所有问题都可以归因到Ambari和麒麟这两个变量上,而不用再怀疑基础配置。
1.3 Ambari与麒麟版本的兼容空间在哪
需要明确一个原则:Ambari管理CentOS集群扩容麒麟节点,本质上就是让你这套新节点去伪装成Ambari认识的操作系统,或者让Ambari支持Kylin这个OS类型。多数情况下,走的是前者。
| 场景 | 麒麟版本情况 | 处理路径 |
|---|---|---|
| Ambari 2.7.6 + HDP 3.1.5 | 麒麟V10 SP1/SP2 x86_64,偏RHEL 7兼容 | 调整OS识别字段后按CentOS 7流程走,问题最少 |
| Ambari 2.7.x + HDP 3.1.x | 麒麟V10较新版本,内核偏RHEL 8 | 需要补依赖,部分组件包可能从RHEL 8源拉取 |
| Ambari 3.x | 麒麟V10 | 相对友好,但仍建议测试验证 |
这里有个实战操作,很多同事问过我:Ambari Agent上报的是/etc/os-release里的信息,Server端拿这个去做OS类型匹配。当Ambari不认识Kylin的时候,最常见也最省事的做法是在麒麟节点的/etc/os-release里做兼容性调整,让它上报成CentOS 7。改之前先备份:
cp /etc/os-release /etc/os-release.bak.$(date +%F)改完之后执行ambari-agent重新注册才会生效。要强调的是,这只是让Ambari的OS检测通过,不是把系统真的变成CentOS。改的时候只动操作系统ID相关的字段,别去碰内核版本、架构字段,否则后续组件里的内核检测脚本会误判。
提示:这种OS识别层的兼容处理属于应急方案。生产环境建议先和系统厂商确认版本适配范围,再决定是否采用。
2. 麒麟节点初始化配置
2.1 系统层配置:hosts、SSH、时钟、防火墙一次性配完
在点Ambari的'Add Hosts'按钮之前,这些基础项的坑一个都躲不过。我直接给出我平时用的操作序列。
主机名和hosts:
hostnamectl set-hostname kylin-dn-104 echo "kylin-dn-104" > /etc/hostname cat >> /etc/hosts <<EOF 192.168.10.10 ambari-server 192.168.10.11 centos-dn-01 192.168.10.12 centos-dn-02 192.168.10.13 centos-dn-03 192.168.10.14 kylin-dn-104 EOFAmbari Server需要通过SSH免密连到新节点执行一系列安装、部署操作。检查Ambari Server上的~/.ssh/id_rsa.pub是否已经加入新节点的/root/.ssh/authorized_keys。注意几个细节:PermitRootLogin yes要打开,UseDNS no建议打开,CentOS节点和麒麟节点都要测试一下双向连通,不只是Server单向连Node。
ssh-keygen -t rsa -b 4096 -N "" -f ~/.ssh/id_rsa ssh-copy-id -i ~/.ssh/id_rsa.pub root@kylin-dn-104 ssh kylin-dn-104 "echo ok"时钟同步这个我吃了不少亏。名字节点和DataNode时间偏差超过一定阈值,块上报会出现异常,甚至导致节点被判为慢节点。老集群用的NTP还是chrony不影响,新节点必须加进来,时钟源和现有集群保持一致:
# 麒麟系统上启用chrony并指向老集群的时间源 systemctl start chronyd systemctl enable chronyd chronyc sources -v防火墙和SELinux直接关掉。没有特殊安全要求的前提下,Hadoop组件之间的端口太多了,你一个个放行会疯掉。Amabari的Agent在注册阶段要连Server的8080(web和api)、8440/8441(agent回连用的通道),而部署阶段又要通过SSH去装包。做完基础验证再开防火墙:
systemctl stop firewalld systemctl disable firewalld sed -i 's/SELINUX=enforcing/SELINUX=disabled/g' /etc/selinux/config setenforce 0最后是透明大页和系统参数。Ambari在加主机时会检查transparent_hugepage,如果开着会告警。生产集群一般建议关闭:
echo never > /sys/kernel/mm/transparent_hugepage/enabled echo never > /sys/kernel/mm/transparent_hugepage/defrag echo 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' >> /etc/rc.local chmod +x /etc/rc.local/etc/security/limits.conf、/etc/sysctl.conf按老节点同样配置拷贝一份。重点是vm.swappiness、fs.file-max,Hadoop在麒麟上跑起来后这些值不对劲的,后面性能调优会很难看。
2.2 基础依赖与JDK:Ambari脚本需要哪些东西
Ambari Agent本身是Python 2.7的脚本集,不是Python 3。麒麟V10很多版本默认的Python可能是2.7.16或者更高,但有些精简版只带了Python 3,这会导致Agent启动直接报语法错误。检查并安装依赖:
python --version yum install -y python python-devel openssl-devel perl nc装完验证一下python命令能不能正常执行。如果系统里同时有Python 3且默认指向3.x,一定要确保/usr/bin/python指向2.7。这个细节比大多数依赖项都要命。
JDK的坑更隐蔽。Ambari把Java Home作为全局配置写在集群里,你在Ambari UI里看到的是Java home这个参数,它指向的是老节点的某个绝对路径。到了新节点上,这个路径也必须存在,否则组件脚本去启动Java进程会失败。
我是直接复制老节点的JDK目录过去,保证二进制和配置完全一致:
# 在老节点打包 tar -czf jdk1.8.0_202.tar.gz /usr/jdk64/jdk1.8.0_202 # 拷贝到新节点并解压 tar -xzf jdk1.8.0_202.tar.gz -C /usr/jdk64/ # 验证 /usr/jdk64/jdk1.8.0_202/bin/java -versionJava 8是HDP 3.1最稳的选择。千万不要在新节点上装个JDK 11或17想'跟上时代',Ambari里的脚本很多硬编码了JDK 8的路径和参数,换版本会牵扯出一堆兼容性问题。这套东西追求的是复制,不是创新。
2.3 yum源:在线还是离线,选型直接决定成败
这是整篇文章我最想重点说的一块。Ambari在注册主机和部署服务时,会在新节点上执行大量的yum安装操作。如果你让新节点直接访问公网的Ambari/HDP仓库,大概率遇到两个问题:一是公网仓库在国内访问极慢,Install操作会反复超时;二是麒麟系统的yum源和老CentOS的源混在一起,依赖解析经常冲突。
我的建议是:无论如何,先在本地准备一个仓库。最简单的做法是直接在Ambari Server上起一个HTTP服务,把需要的rpm包放进去,然后新节点把Ambari repo指向这台Server。
# 在Ambari Server上 yum install -y httpd createrepo mkdir -p /var/www/html/ambari-repo # 把从官方源拉下来的ambari-agent及相关依赖rpm包放进来 cd /var/www/html/ambari-repo createrepo . systemctl start httpd systemctl enable httpd麒麟节点上的repo文件长这样:
[ambari-local] name=ambari-local-repo baseurl=http://ambari-server-ip/ambari-repo gpgcheck=0 enabled=1如果你想用Ambari自带的Local Repository功能,可以在Ambari UI里操作:Admin -> Repo Management -> Local Repositories,把HDP和Ambari的baseurl都指向本地HTTP地址。这个设置会在Ambari向新节点下发任务时自动注入,节点不用手动改repo,省很多事。
# 验证repo是否生效 yum clean all yum makecache yum list available | grep ambari-agent这一步的意义在于:后面的所有安装动作都变成了局域网内拷贝,速度快,失败率低。生产环境扩容最怕的就是安装包下载到一半网络超时,然后整个Ambari操作卡在一个'Installing'的状态里,进退不得。
3. Ambari Agent接入与节点注册
3.1 装Agent的两种姿势:yum装还是手动拷
Ambari的Agent安装看起来简单,一个yum install ambari-agent就完事,但麒麟节点上它不一定这么听话。如果Ambari Server已经通过Local Repositories配置好了源,那就直接装:
yum clean all yum makecache yum install -y ambari-agent装完看版本,确认和Ambari Server的版本完全一致:
ambari-agent --version如果yum源拉不到,或者网络环境确实装不上,还有一个备选方案:直接从老节点把ambari-agent的rpm包拷贝过来手动安装。这个方案在只有三四台新节点的时候非常实用,不用折腾本地仓库的HTTP服务:
# 在老节点上找到rpm缓存 ls /var/cache/yum/x86_64/7/ambari/packages/ # 把rpm拷到新节点 scp ambari-agent-2.7.6.0-*.x86_64.rpm root@kylin-dn-104:/root/ # 在新节点安装 rpm -ivh ambari-agent-*.x86_64.rpm手动rpm安装需要注意依赖。缺少什么依赖,rpm -ivh会直接告诉你,然后逐个补齐。有些依赖在麒麟系统的官方源里有,那就yum install补齐;如果官方源里也没有,再从老节点或仓库里拷。
3.2 修改agent配置并启动:代理的心跳要靠这个文件
装完Agent之后,第二步是让Agent知道去连哪个Ambari Server。Agent的配置文件在/etc/ambari-agent/conf/ambari-agent.ini,核心就是hostname这个字段:
# 先备份 cp /etc/ambari-agent/conf/ambari-agent.ini /etc/ambari-agent/conf/ambari-agent.ini.bak vi /etc/ambari-agent/conf/ambari-agent.ini找到这一段:
[agent] # hostname=localhost hostname=ambari-server-ip或者用官方推荐的方式:
ambari-agent reset ambari-server-ipreset命令会重新初始化Agent的配置和连接状态,适合Agent之前被别的集群用过的情况。如果Agent之前注册过其他Server,不reset直接改配置文件可能会残留旧的注册信息。
启动Agent:
ambari-agent start启动后立刻看日志:
tail -f /var/log/ambari-agent/ambari-agent.log正常情况下会出现经常刷屏的状态:Connected to Ambari Server。如果一直是Sleeping或者报Failed to connect,先检查网络、hostname、防火墙。这个阶段问题相对干净,基本就是不通和不通。
注意:启动Agent要用
ambari-agent start,不要用systemctl start ambari-agent。虽然麒麟系统上service脚本也在,但直接跑二进制命令更稳,报错信息也更直白。
3.3 在Ambari Web UI上完成注册和角色分配
Agent起来只是一半,另一半要在Ambari UI上点出来。路径是Hosts -> Add New Hosts,填上主机名点搜索,Ambari会去探测节点并显示一系列检查项。
这一步有个很常见的情况:Ambari检查列表里,OS类型会显示成Kylin或Unknown,Ambari状态是黄色或红色。如果你前面的/etc/os-release已经做了兼容调整,这步显示的就会是CentOS 7,检查项基本全绿。
检查项点开后,实际看这几个:
- Python版本:2.7最稳,3.x要小心
- 内核参数:透明大页是否关闭
- 包管理器:yum是否正常
- 磁盘空间:
/tmp、/var这些目录空间是否够
检查通过之后,进入Role分配和目录配置页面。这里要把新节点上要部署的角色勾上。以HDFS和Yarn扩容为例,重点勾DataNode和NodeManager:
- DataNode:配置
dfs.datanode.data.dir,填上你挂载的数据盘路径,比如/data1/hadoop/hdfs/data,/data2/hadoop/hdfs/data - NodeManager:配置
yarn.nodemanager.local-dirs和yarn.nodemanager.log-dirs,同样指向规划的磁盘路径 - 如果老集群还有HBase RegionServer,新节点内存够的话可以勾上
目录配置这里特别强调:路径要和现有节点保持相同的约定风格。比如老节点都是/data1/hadoop/hdfs/data这种带hadoop子目录的结构,新节点也照做。这样后面排查问题时,路径一看就明白。
点Deploy之后,Ambari会向新节点下发安装任务。别关浏览器,也别切页面,盯着进度条看。正常情况下会经过Install packages -> Start services这个过程。如果卡在某个百分比超过十分钟,去节点上看Agent日志:
tail -200 /var/log/ambari-agent/ambari-agent.log大多数卡住的情况都是yum装包卡住,或者某个rpm包依赖解析失败。这时候看日志里报的具体包名,单独处理掉,然后回UI点击Retry。
4. 服务部署中的踩坑与排障实录
4.1 高频报错与解决办法速查表
我把这次扩容和自己的历史排障经验整成了一张表,基本都是高频出现的。每个坑都是实际踩过的,照着排查能省不少时间。
| 报错或现象 | 根因 | 解决办法 |
|---|---|---|
Cannot retrieve repository metadata (repomd.xml) | yum源不可达或repo配置不对 | 重配本地repo,yum clean all && makecache |
OS not supported/ 主机标红 | Ambari不认识麒麟系统 | 调整/etc/os-release兼容字段并重启Agent |
Unable to connect to host | SSH免密没配好或端口不通 | 检查authorized_keys、PermitRootLogin、SSH端口 |
Agent日志里Failed to resolve host | /etc/hosts和hostname没写对 | 统一修改所有节点hosts文件,确认hostname唯一 |
部署DataNode时No such file or directory | JDK路径不一致 | 把/usr/jdk64/jdk1.8.0_202完整拷到新节点 |
Operation timed out | 下载rpm包超时 | 用本地仓库,或调大yum timeout参数 |
页面一直显示Installing不前进 | yum锁被占用或慢下载 | 看Agent日志定位包名,单独处理 |
Permission denied在格式化目录 | 目录权限不对 | chown -R hdfs:hadoop /data1 |
Java not found | Ambari的Java home配置和节点实际路径不一致 | 全局检查Java home,确保所有节点路径一致 |
还有一个特别隐蔽的坑:Ambari UI上执行某个组件的Start操作,结果组件起不来,但Agent日志和组件日志都不报错。后来发现是麒麟节点的/etc/resolv.conf里DNS配置有问题,导致组件之间通过主机名互相访问失败。建议每台节点都确认一下local DNS或hosts解析,不要指望所有节点只靠hosts文件就万事大吉。
4.2 数据目录挂载与权限分配细节
这一节是我每次扩容都痛一次的地方。新机器预装系统的人往往只分了一个系统盘,数据盘全是裸盘。你需要在部署服务之前把所有DataNode目录准备好,不然Ambari去执行格式化时会找不到目标路径。
操作序列大概是这样的:
# 查看新磁盘 lsblk -f # 格式化数据盘为xfs mkfs.xfs /dev/sdb mkfs.xfs /dev/sdc # 规划挂载点 mkdir -p /data1 /data2 # 写入fstab,避免重启丢失 echo '/dev/sdb /data1 xfs defaults 0 0' >> /etc/fstab echo '/dev/sdc /data2 xfs defaults 0 0' >> /etc/fstab # 挂载 mount -a # 创建Hadoop目录结构 mkdir -p /data1/hadoop/hdfs/data /data2/hadoop/hdfs/data mkdir -p /data1/hadoop/yarn/local /data2/hadoop/yarn/local mkdir -p /data1/hadoop/yarn/logs /data2/hadoop/yarn/logs # 授权 chown -R hdfs:hadoop /data1 /data2 chown -R yarn:hadoop /data1/hadoop/yarn /data2/hadoop/yarn权限这步极其关键。Ambari在格式化DataNode目录时会切换到hdfs用户去执行,目录如果属于root,格式化会直接失败。Yarn的目录属于yarn用户和hadoop组。这些用户应该是Ambari在装Agent时已经建好的,如果没建,你要手动创建:
useradd -r hdfs useradd -r yarn挂载的时候顺带把discard或noatime加上也行,线上环境追求稳定就defaults够了。文件系统用XFS是主流,别用ext4。Hadoop在XFS上的大文件读写性能更稳,这也是老节点的一致选择。
4.3 上线后的验证与回滚预案
部署完成不等于扩容成功,一定要在老集群视角看到新节点真正干活了才算数。
HDFS侧验证:
hdfs dfsadmin -report输出里会多出新的DataNode列表,容量、块数、最后心跳时间都正常。然后到NameNode Web UI上看,新节点的Datanode状态是In Service,不是Stale。
Yarn侧验证:
yarn node -list -allResourceManager确认新NodeManager节点状态是RUNNING,健康状态Normal。
跑一个简单的验证任务,用hadoop自带的小工具往新节点上写文件:
hadoop jar /usr/hdp/current/hadoop-mapreduce-client/hadoop-mapreduce-examples.jar pi 10 100跑完看一下任务日志,确认container有没有跑到新节点上。
回滚预案要提前想好。如果发现新节点有问题,最糟糕的情况是DataNode已经注册进集群且开始收副本了。这时候直接停Agent、从Ambari里删主机会非常危险,会导致HDFS副本数不足,触发大量补副本甚至数据丢失风险。
正确顺序是:
- 在Ambari UI把新节点的DataNode标记Decommission。
- 等待NameNode把该节点的块全部迁移到其他节点,
hdfs dfsadmin -report里该节点变为Decommissioned。 - 停掉NodeManager和DataNode组件,从Ambari Hosts里移除节点。
- 最后再停Agent。
如果只是Agent注册阶段出问题,还没部署服务组件,那就简单多了,ambari-agent stop,然后UI上删掉主机记录即可,不影响集群。
我个人的扩容习惯是把新节点分成两批:先加一台最核心的DataNode和NodeManager组合,跑三到五天,观察心跳、块上报、Yarn资源使用都稳定了,再加剩下的节点。这样做的好处是,即使麒麟节点上有潜在问题,影响面也被控制住了。
最后再分享一个小技巧:Ambari的Agent日志和组件日志是两个地方。组件起不来,别只盯着Ambari UI上的红点,直接去节点上看/var/log/hadoop/hdfs/和/var/log/hadoop/yarn/,很多错误信息在Ambari UI上是看不到的。这次扩容我在麒麟节点上排查DataNode启动失败,就是靠看hadoop-hdfs-datanode-*.log里那句Version mismatch定位到JDK路径问题。扩容这种事,稳住一次就能总结出自己的一套打法,后面再遇到就都是熟练工了。