CentOS定制ISO实战:Kickstart无人值守安装与镜像重打包指南

发布时间:2026/9/13 14:33:04
CentOS定制ISO实战:Kickstart无人值守安装与镜像重打包指南 搞运维的人应该都有这种体会新机器装系统不是最烦的最烦的是装完之后那几十条初始化命令。配IP、改主机名、关防火墙、装编译工具、设置yum源……一台台重复敲敲到怀疑人生。我自己曾经连续一个下午给十几台VMware虚拟机装CentOS装完一台手动配置一台后来实在受不了才认真研究了一下定制ISO镜像这件事。其实CentOS定制打包的原理并不复杂核心就两件事一是把安装过程中要执行的初始化操作写进Kickstart简称KS脚本二是把修改后的文件重新打包成ISO。做完一次以后同版本的机器全都能无人值守部署装完开机就是一个能直接干活的系统。这篇文章把我踩过的坑和验证过的方案完整写出来内容包括轻量定制修改引导、植入KS脚本和进阶玩法增删RPM包、重建仓库适合有Linux基础、需要批量部署系统或想给团队做标准化系统模板的运维和测试同学参考。1. 定制镜像的整体思路1.1 定制到底解决什么问题很多人一开始的想法是“装完系统我再跑个shell脚本不就行了”理论上确实可以但实际批量部署时你会发现几个痛点第一新系统装完没有网络环境或者源站不在内网脚本里依赖外网下载的包全部抓瞎第二装机过程本身仍然需要人工交互选语言、选磁盘、设密码一步都不能少人还是得守在机器旁边第三每台机器硬件配置可能都一样但分区策略、软件包集合、内核参数这些如果不统一后面维护就是灾难。定制ISO的真正价值在于把“人工交互”变成“无人值守”把“装完再配置”变成“装完即配置好”。Kickstart文件里可以定义分区、时区、网络、密码、软件包甚至可以用%post段落执行任意shell命令。镜像里自带的仓库和软件包保证了安装全程不依赖外网这对内网环境简直是救命稻草。1.2 轻量改包与全自动部署两条路线做定制ISO大致有两条路线。一条是“轻量定制”就是在原始ISO里修改isolinux引导配置、加一个ks.cfg文件可能有需要的话再往Packages目录里丢几个自写的RPM包然后重新打包。这个方案改动小、速度快、出问题容易排查也是本文的重点。另一条是“彻底重制”用livecd-tools或者lorax这类工具从零构建一个系统镜像控制力最强但复杂度也高你不仅需要理解完整的构建链路还要在构建过程中解决依赖解析、压缩格式、引导兼容这些问题。对于绝大多数场景我认为轻量定制已经足够没必要一上来就上重武器。我见过不少群里问“定制CentOS镜像哪家强”的新手最后发现他们要的其实就是轻量定制加一个靠得住的ks.cfg。2. 准备工作与基础环境2.1 工具清单打包ISO这件事在Linux环境里做会比Windows顺手得多推荐准备一台CentOS 7或兼容的Linux机器主要是用到下面几个工具mkisofs/genisoimage生成ISO镜像的核心工具CentOS里通常由genisoimage包提供createrepo重新生成仓库元数据往Packages目录里加过RPM包就必须用它rsync从官方ISO里同步文件到工作目录比cp速度快且干净isomd5sum给ISO植入校验和属于可选但建议加上用于生成加密密码的工具比如grub-crypt或openssl如果手头连Linux机器都没有先在虚拟机里装一个最小版CentOS就行工具就几条yum命令的事。yum -y install genisoimage createrepo rsync isomd5sum2.2 原始ISO的获取与校验做定制逻辑上需要拿到对应版本的原始ISO建议直接去官方或国内高校镜像站下载CentOS 7.9的DVD版而非Minimal版。为什么用DVD版因为DVD版自带了大部分常用RPM包定制后可以把安装仓库指向本地介质全程不需要联网Minimal版虽然体积小但软件包太少定制空间有限。下载完先做校验用sha256sum核对官方hash值防止文件损坏或者下载不完整。这一步很多人会跳但如果源ISO本身有问题后面所有工作都是白搭。sha256sum CentOS-7-x86_64-DVD-2009.iso确认无误后把ISO挂载到/mnt/centos_iso然后把内容同步到一个可写的工作目录比如/srv/custom_centos。注意同步时保留权限和软链接否则后面引导会有问题。mount -o loop CentOS-7-x86_64-DVD-2009.iso /mnt/centos_iso mkdir -p /srv/custom_centos rsync -a /mnt/centos_iso/ /srv/custom_centos/做完这一步工作目录里应该能看到isolinux、images、Packages、repodata这些典型的ISO结构目录。3. 核心实操重新打包完整流程3.1 理解ISO目录结构与引导机制在动手改东西之前先花两分钟搞清楚ISO里几个关键目录的职责。isolinux目录存放的是BIOS引导相关文件里面有一个isolinux.cfg控制着开机菜单和默认内核参数这是轻量定制的入口。images目录里有efiboot.img对应UEFI引导负责让ISO在EFI模式下也能正常启动。Packages目录是所有RPM包的集合repodata目录则保存仓库元数据安装器靠它解析依赖关系。这个结构理解透了你就能解释很多诡异问题。比如“为什么我改了isolinux.cfg但安装时还是进了原始安装界面”多半是因为你没有处理EFI引导路径再比如“为什么我自己加的包在安装时找不到”多半是Packages目录更新了但repodata没重建。3.2 修改引导配置与默认启动项isolinux.cfg通常是这样的结构default vesamenu.c32 timeout 600 label linux menu label ^Install CentOS 7 kernel vmlinuz append initrdinitrd.img inst.stage2hd:LABELCentOS\x207\x20x86_64 quiet我最常用的做法是保留默认的Install条目再新增一个custom条目作为默认启动项这样原始安装功能还在出问题也能回退。修改后的关键部分是append那一行加上kscdrom:/ks.cfg同时把inst.stage2的卷标改成后面打包时要用的卷标。default custom timeout 100 label custom menu label ^Install CentOS 7 Custom kernel vmlinuz append initrdinitrd.img inst.stage2hd:LABELCentOS-7-Custom kscdrom:/ks.cfg quiet label linux menu label ^Install CentOS 7 Original kernel vmlinuz append initrdinitrd.img inst.stage2hd:LABELCentOS-7-Custom quiet这里的坑有两点。一是timeout单位是1/10秒100就是10秒设太短人还没看清菜单就进默认项了我一般设100到300之间。二是inst.stage2指定的LABEL必须和后面mkisofs的-V参数完全一致大小写、连字符都不能差否则安装器找不到安装源直接卡在“不能从CDROM读取”的报错界面。我一开始就是用默认LABEL结果每次都要手工切到命令行才能继续很被动。3.3 编写Kickstart文件ks.cfg是整个定制过程的核心我直接给一份能用的模板再逐段解释关键参数。#versionDEVEL install cdrom lang en_US.UTF-8 keyboard us network --bootprotodhcp --deviceens33 --onbootyes rootpw --iscrypted $6$xxx user --nameadmin --groupswheel --password$6$yyy --iscrypted timezone Asia/Shanghai --isUtc text skipx zerombr clearpart --all --initlabel part /boot --fstypexfs --size1024 part pv.01 --size1 --grow volgroup vg_sys pv.01 logvol / --fstypexfs --namelv_root --vgnamevg_sys --size20480 logvol swap --namelv_swap --vgnamevg_sys --size4096 logvol /home --fstypexfs --namelv_home --vgnamevg_sys --size10240 reboot %packages --ignoremissing core development vim wget net-tools lsof tcpdump tar unzip ntpdate %end %post --log/root/ks_post.log # 配置内网或国内vault镜像源 cat /etc/yum.repos.d/CentOS-Base.repo EOF [base] nameCentOS-7 - Base baseurlhttp://mirrors.aliyun.com/centos-vault/7.9.2009/os/x86_64/ gpgcheck0 [extras] nameCentOS-7 - Extras baseurlhttp://mirrors.aliyun.com/centos-vault/7.9.2009/extras/x86_64/ gpgcheck0 [updates] nameCentOS-7 - Updates baseurlhttp://mirrors.aliyun.com/centos-vault/7.9.2009/updates/x86_64/ gpgcheck0 EOF # 系统初始化 systemctl disable firewalld systemctl enable sshd echo alias vivim /etc/profile echo export LANGen_US.UTF-8 /etc/profile timedatectl set-ntp true %end逐段拆解一下关键设计的理由。网络配置里我没有写死IP而是用dhcp加固定网卡名ens33因为定制镜像通常要在多台机器上用写死IP反而麻烦。如果你有网络规划也可以改成静态IP但建议把DNS和网关也一并写上。分区方案我用LVM而不是标准分区原因是LVM后续扩容方便我在生产环境里经常遇到“根分区满了要加盘”的需求逻辑卷在线扩容比直接扩分区省事得多。根卷我给了20Ghome给了10Gswap给了4G。这里要说明一下swap大小按经验一般是物理内存的1到2倍但超过8G物理内存的机器不必给太多4到8G就够具体还要看跑什么业务。%packages段落里的--ignoremissing参数很重要。因为镜像里的包版本和组定义可能跟你ks.cfg里写的不完全对应加上这个参数后即使个别包缺失也不会中断安装只会跳过并记录警告。否则安装时会因为一个包找不到就报错退出排错非常烦躁。至于group这种写法可以理解成一组包的集合core就是最小核心环境development会装编译工具链这是给开发机和编译场景准备的。%post段落里配置的镜像源是整个定制里最实用的部分。CentOS 7已经进入维护末期官方源默认指针已经指向vault归档直接yum装包经常慢得让人崩溃。我把它换成阿里云的vault地址速度快且稳定。你可以根据自己所在地区换成清华、中科大或者其他镜像站原理一样。注意这里的heredoc写法EOF要加引号防止变量展开否则$符号会被解释成空变量配置文件内容就全乱了。3.4 重建仓库元数据并重新打包如果你没有新增或者删除Packages目录里的任何RPM包可以跳过createrepo这一步。但只要动过包哪怕只是加一个自己打的rpm就必须重建仓库元数据否则安装器在解析依赖的时候根本不知道这个包的存在即使文件躺在Packages目录里也白搭。cd /srv/custom_centos rm -rf repodata createrepo -g /srv/custom_centos/repodata/*.xml .这里有一个细节值得提醒createrepo的-g参数原本是用来指定组信息的正常应该指向原repodata目录里那个带有comps的XML文件。但如果你已经删掉了原repodata再运行这条命令就会因为找不到组文件而警告。保险的做法是先备份一份repodata重建时把comps文件指进去。这个只影响安装时软件包分组的选择不影响基础安装。之后把ks.cfg复制到工作目录的根下名字必须是ks.cfg或者至少要和isolinux.cfg里指定的路径一致。然后就是打包cd /srv mkisofs -o centos7-custom.iso \ -b isolinux/isolinux.bin -c isolinux/boot.cat \ -no-emul-boot -boot-load-size 4 -boot-info-table \ -R -J -T -V CentOS-7-Custom \ -eltorito-alt-boot -e images/efiboot.img -no-emul-boot \ custom_centos/一个个参数说清楚。b参数指定BIOS引导文件c参数指定引导目录表R和J是为了在光盘上保留Unix权限和生成Windows可读的Joliet扩展名T参数会生成一些转换文件V就是卷标必须跟isolinux.cfg里inst.stage2的LABEL一致。eltorito-alt-boot和e参数是把EFI引导文件也写进镜像这样UEFI模式安装时就能正常启动。不加这条UEFI启动的机器会直接黑屏或引导失败。打完包后建议再用implantisomd5给ISO加一个校验和体积很少但可以防止后期拷贝损坏。implantisomd5 centos7-custom.iso最后把ISO放到VMware里开一台新虚拟机测试选择CD/DVD指向这个ISO然后开机看效果。第一次装的时候人会比较紧张因为不知道会不会卡在哪一步我的建议是手边开着串口控制台或者保持VMware窗口不最小化这样能第一时间看到安装器的输出。4. 高级玩法增删软件包与仓库调整4.1 如何引入自编RPM或第三方包如果团队内部有自己封装的RPM比如统一的监控agent、日志采集器、定制内核模块把这些直接放进镜像里是最省事的交付方式。操作步骤也不复杂先把RPM文件拷到Packages目录然后用createrepo重建repodata最后在ks.cfg的%packages段落里加上包名。这里有一个依赖上的坑。你自己打的RPM包经常依赖一些基础开发库而原版DVD里可能没有这些依赖安装时就会报“缺少依赖”导致包装不上。解决办法是两个方向要么在打包RPM的时候尽量静态编译要么把这个依赖也用yumdownloader拉下来一起塞进Packages目录保证仓库里所有依赖都能闭环。我在做监控agent时就遇到过这种问题把libpcap相关的包一起放进去才解决。另外注意架构一致性Custom ISO里Packages目录大部分是x86_64包如果你的自研软件里有i686依赖安装器会警告很多时候也会直接失败。建议所有额外包统一用x86_64。4.2 精简软件包的收益与风险有些人是反向操作希望把镜像里用不到的大包删掉让ISO更小。这个思路在理论上是可行的DVD原始体积约4G删掉图形界面、多余语言包、打印机驱动之后可能压缩到2G以内。但也要承担代价如果你删错了包比如某个运行库被另一个软件依赖安装时依赖解析就会挂掉到时候得一个一个翻日志找是谁依赖谁排错非常痛苦。我的建议是除非你对镜像里的包依赖关系了然于胸否则不要轻易删包。真正想瘦身应该走Minimal版本的重新打包路线那才是一开始就冲着精简去的方案。DVD定制的主要价值是让安装过程自动化和初始化配置标准化而不是为了省那几G空间。如果硬盘和网络带宽都不紧张保留完整包其实是更稳妥的选择。4.3 修改默认时区、语言和内核参数时区、语言这类参数直接改ks.cfg就能生效前面模板里已经写了timezone Asia/Shanghai。内核参数如果要在安装时就加修改isolinux.cfg的append行即可比如常见的内核参数有net.ifnames0关闭网卡名随机化、crashkernelauto保留崩溃内存等。关于默认语言有些人希望安装完系统自带中文环境只需要在ks.cfg里设置lang zh_CN.UTF-8然后在%packages里加入languages相关包比如langpacks-zh_CN。不过我自己通常建议运维机器保持英文环境中文字体在终端里经常出现乱码处理起来比英文环境麻烦得多。如果你确实需要中文记得把kde-l10n-Chinese或glibc-langpack-zh这类包放进去。5. 常见问题与排查技巧实录5.1 踩坑记录与解决方案直接上我遇到过的几个真实问题做成速查表大家在操作时可以直接对照。现象根本原因解决办法安装器提示找不到安装介质mkisofs的-V卷标和isolinux.cfg里inst.stage2的LABEL不一致统一两处卷标名称重新打包UEFI模式开机黑屏或无法引导打包时漏了eltorito-alt-boot和-e images/efiboot.img参数补上EFI引导参数后重新mkisofs%post脚本里的yum源内容被截断或变量被展开heredoc的EOF没加引号shell提前解析了$改用EOF防止变量展开安装卡在软件包依赖解析阶段添加了RPM包但没重建repodata删掉repodata后用createrepo重建ks.cfg里rootpw明文密码报警告安装器检测到弱密码格式用openssl passwd -6生成加密哈希替换安装完重启后没有网络ks.cfg里network配置缺失或网卡名不匹配查看实际网卡名在%post中通过nmcli配置静态或DHCP网络装完没有vim只有vivi是基础包自带vim需要显式加入在%packages中加上vim和vim-enhanced这里面我想多说一下“找不到安装介质”这个问题它几乎占了定制ISO排障的一半。原因就是mkisofs的-V参数与isolinux.cfg里的LABEL不一致。比如你-V写的是CentOS-7-Custom但isolinux.cfg里还留着原始的CentOS 7 x86_64两者对不上安装器在空中找不到卷标只能报错。这个坑很隐蔽因为ISO能正常引导菜单也能弹出来问题出在引导内核之后找不到安装源排查思路要往这个方向靠。还有一次我遇到“快到100%时报错安装程序崩溃”最后发现是磁盘分区的时候clearpart把虚拟磁盘清掉了但因为我是用串口做远程安装没人及时发现交互界面弹了个磁盘大小确认框。这个属于安装交互层的问题真正解决的办法是在ks.cfg里加上zerombr让安装器自动确认清盘或者在测试阶段就保持VMware console窗口可见。5.2 如何验证镜像是否定制成功验证这件事最好在VMware或者VirtualBox里做用自己的镜像创建一台虚拟机然后仔细观察安装过程。第一看引导菜单开机后应该出现你自己定义的custom条目且倒计时结束后自动进入。如果还是默认进原始安装菜单说明isolinux.cfg没改对或者default指定的label名写错了。第二看安装过程如果ks.cfg生效安装界面会根据你的配置自动进行分区、设置密码、选择软件包全程不需要人工介入。如果中途卡在某个交互界面十有八九是ks.cfg里某个参数有语法错误或版本不匹配。我建议在ks.cfg开头加一行#versionDEVEL兼容性最好不然老版本安装器可能不认。第三看安装后环境重启后登录系统检查主机名、IP、时区、防火墙、DNS、yum源是否都符合预期。通常我会在%post里把关键信息都写入/root/ks_post.log排障时直接看这个文件比逐个敲命令高效得多。5.3 定制ISO在虚拟机上的特殊注意事项如果你主要是在VMware里用这些定制镜像有一个参数值得注意虚拟硬件版本和固件类型。VMware默认可能是BIOS也可能是UEFIBIOS对应isolinux引导UEFI对应efiboot.img引导。如果镜像两个引导都做了一般没问题但如果你跳过了EFI引导参数最好把虚拟机的固件类型改成BIOS。另外VMware磁盘控制器一般是LSI Logic SAS或PVSCSI某些情况下Linux内核可能在安装阶段认不出磁盘导致分区失败。遇到这种情况在VMware里把磁盘控制器改成LSI Logic并行或者SATA控制器能绕开很多兼容性问题。这个跟镜像本身关系不大但会在“为什么我用定制ISO装机总失败”的排查清单里非常有用所以我特别列出来。6. 一点实操体会做了这么多次定制镜像我个人最大的体会是Kickstart的力量远比想象中大很多人以为它就是无人值守安装实际上它还能配合%post做很多事情。比如我们可以把系统加固的基线脚本写进去把监控agent、日志采集器预装好把内部DNS和NTP配置好甚至把SSH公钥直接植入指定用户的authorized_keys里。这样分发下去的机器从第一次开机就已经处在受控的、可运维的状态这种“出厂即标准”的感觉用过一次就回不去了。如果你正好被重复装机折磨着花一个下午把这个流程跑通后面的日子会轻松非常多。