作为一个常年跟 Linux 服务器打交道的人,我越来越觉得“手里有粮,心里不慌”这句话太对了。这里的“粮”,指的就是像 RHEL 9 这样的系统安装镜像——特别是那种完整的 DVD ISO 安装包。在隔离的内网、机房现场、或者网络状态不太稳定的环境里,用一份 RHEL 9 的 DVD ISO 完成离线安装,并且把它变成随时可用的本地软件仓库,是我测试过无数次、也最推荐的做法。
这篇文章我会把整个流程完完整整地拆开讲:从下载哪种 ISO 文件、怎么校验完整性、怎么制作启动盘,到安装过程中的分区和软件选择,再到装完系统后怎么把这个 ISO 挂载成 dnf 能用的本地源。每一步我都会说明为什么这么做,把我踩过的坑和需要注意的细节一并写出来。无论你是第一次接触 RHEL 9,还是需要在离线环境里快速交付系统的运维同行,这份实操记录应该都能帮你少走一些弯路。
1. 为什么我建议用DVD ISO装RHEL 9
1.1 DVD ISO和最小化ISO到底差在哪儿
RHEL 9 官方提供的安装镜像主要分两类:一类是 DVD ISO,体积通常在 8GB 到 10GB 左右;另一类是 Boot ISO,体积只有几百 MB。很多人第一反应是 Boot ISO 更小、下载快,所以选了它。真到安装的时候才发现,Boot ISO 启动后还需要从一个 HTTP、HTTPS 或 NFS 软件源拉取安装包和系统文件。如果所处的网络环境里没有现成的安装源,安装过程根本走不完。
DVD ISO 则完全不同,它把完整的安装程序和软件仓库直接打包在了镜像里。安装过程中所有需要的 RPM 包都能从镜像内部就地读取,全程不依赖外部网络。这一点在隔离网、机房内网以及没有配置本地软件源的场景里非常关键。而且,这个 ISO 不只是在安装阶段有用——装完系统之后,它依然可以继续挂载使用,作为本地仓库,用来安装后续需要的软件,比如 httpd、nginx、python3 这些常见的服务组件。
体积大一些、还得单独准备一个装得下的 U 盘,这是它的代价,但换来的是一个不受网络状态影响的完整安装环境。我个人的习惯是:只要不是临时尝鲜,一律用 DVD ISO。它带来的省心程度,远远超过那一点下载时间和磁盘空间的成本。
1.2 什么场景下该走DVD ISO这条路线
我总结下来,有这几类场景最值得走 DVD ISO 这条路。第一类是物理服务器所在的机房没有外网,或者外网带宽很小,在线安装根本不现实。第二类是公司内部网络有严格的访问控制,默认的 yum/dnf 仓库源无法访问外部服务器。第三类是团队需要批量交付同样的系统环境,用 DVD ISO 可以保证每台机器安装的软件版本完全一致,不会因为在线源版本浮动而出现环境差异。第四类是希望在安装过程中不被订阅、账户、网络认证这些环节打断,一次性在本地完成安装。
需要特别说明的是,RHEL 9 虽然可以跳过 Red Hat 账号注册完成安装,但后续使用 dnf 安装在线软件仓库时,通常还是需要有效的订阅。DVD ISO 自带的本地仓库不需要网络,也不依赖订阅就能正常搜索和安装镜像内的软件包,这一点对实验室或内部环境尤其友好。如果你只是需要一套能跑起来的 RHEL 9 系统,不想牵扯订阅那一套,那 DVD ISO 几乎是最合适的途径。
还有一点容易混淆:“Red Hat Linux 9”是很久以前的老版本系统(2003 年前后),和现在的 Red Hat Enterprise Linux 9 完全是两代产品。现在大家说 redhat 9 / RHEL 9,基本都指 RHEL 9,内核、安装器、包管理工具都是现代化的一整套,千万别拿老古董的经验往新版本上套。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 安装前准备:下载、校验与启动介质
2.1 正确的镜像下载入口与文件选择
RHEL 9 的正式镜像下载不提供公开匿名通道,需要先有一个红帽账号,并在红帽客户门户里完成订阅绑定。之后进入 Downloads 页面,选择 Red Hat Enterprise Linux 版本,就能看到 DVD ISO 下载选项。ISO 文件的命名一般长这样:rhel-9.3-x86_64-dvd.iso,其中 9.3 是具体的次版本号,x86_64 是 CPU 架构,dvd 表示这是完整的 DVD 镜像。如果服务器是 ARM 架构,记得要找 aarch64 版本,不要下错。
下载的时候有个细节:浏览器直接下载大文件偶尔会断流,浏览器自带的断点续传机制也不太好用。如果下载通道不稳定,建议从下载页面把 ISO 的完整链接复制出来,用命令行工具下载,比如 wget -c 断点续传,会比浏览器省心得多。下载完成后不要急着把文件拷来拷去,第一步应该先做完整性校验,这一步非常关键,直接决定了你能不能用这个镜像正常安装。
2.2 校验ISO完整性:拿什么算、怎么算
ISO 镜像在传输过程中可能因为网络问题损坏,而安装器对损坏的镜像往往没有太友好的提示,最后的表现可能是启动卡住、找不到安装文件,甚至分区到一半报错。与其在安装现场抓瞎排查,不如下载后花一分钟做一次完整性和安全性校验。
红帽官网下载页面会提供对应的 SHA-256 校验值。在 Linux 环境下,执行:
bash复制sha256sum rhel-9.3-x86_64-dvd.iso
把输出的哈希值和官网提供的字符串逐位比对,一致说明文件完整。如果是在 Windows 环境里,用 PowerShell 也能同样校验:
powershell复制Get-FileHash .\rhel-9.3-x86_64-dvd.iso -Algorithm SHA256
比对的时候不要只看前几位,字符串比较要逐位检查。还有一个容易被忽略的细节:校验值必须和下载的版本严格对应,9.3 的 ISO 不能用 9.2 的校验值去比对,x86_64 的镜像和 aarch64 的镜像哈希也必然不同。在实际操作中,我见过有人因为贴错校验值,误以为自己下载的镜像损坏,白白重新下了一遍。
2.3 制作USB启动盘还是直接挂载ISO
拿到完整 ISO 之后,安装介质有两种常见选择。物理服务器上通常会写进 U 盘,用 U 盘引导启动。写盘工具我推荐用 dd 或 balenaEtcher 这类直接写镜像的工具。在 Linux 主机上写入的命令大致如下:
bash复制sudo dd if=/path/to/rhel-9.3-x86_64-dvd.iso of=/dev/sdX bs=4M status=progress && sync
这里有一个特别容易出错的细节:of 参数指向的必须是整块设备,比如 /dev/sdb,而不是 /dev/sdb1 这种分区节点。如果写到了分区节点上,大概率会写坏分区表,甚至可能把系统搞到无法启动。实际操作前务必先用 lsblk 核对目标盘符,确认这个磁盘是你真正要写入的 U 盘,而不是某个数据盘。dd 写入完成后不会有什么友好提示,一旦写错盘,数据基本找不回来。
如果是在虚拟机环境里安装,就不需要刻录 U 盘了。以常见的虚拟化平台为例,直接把下载好的 ISO 挂载到虚拟机的 CD/DVD 光驱上,并把启动顺序调整为光驱优先即可。一些虚拟化平台还支持直接从 ISO 文件启动安装器,效率和 U 盘几乎一样。唯一要留意的点是 RHEL 9 的镜像比较大,虚拟机光驱挂载时建议直接使用 ISO 所在的实际文件路径,而不要反复拷贝到多个数据存储,否则多台虚机同时安装时 IO 压力会非常明显。
3. 一步步装完RHEL 9:我的安装现场记录
3.1 启动引导与安装界面选项
从 ISO 或 U 盘启动后,会进入 GRUB 引导界面,默认选中的是 “Install Red Hat Enterprise Linux 9.3” 这一项。这时候我一般会按 Tab 键或 e 键快速看一下启动参数,确认 inst.stage2 指向的是正确的镜像位置。大多数情况下直接回车用默认参数就能正常进入安装器,但我在实践中遇到过 U 盘在部分服务器上识别不稳定的情况,这时候通常会在启动参数后面追加 inst.dd,或者改用 inst.stage2=hd:LABEL=RHEL-9-3-0-BaseOS-x86_64 这种写法,强制指定镜像所在设备。
安装器 Anaconda 启动后,第一步是选择语言。这一步选什么语言影响的是安装界面和系统默认语言环境,对服务器本身功能影响不大。接着就会看到安装信息摘要页面。RHEL 9 在这个页面把关键配置项集中展示,包括安装目的地、软件选择、root 密码、用户创建、网络和主机名等,这些配置没完成前,“开始安装”按钮是灰的,没法点。
3.2 安装目标与手动分区
安装信息摘要页面里,最重要的一项就是“安装目的地”。如果直接把一块磁盘选上并保持自动配置,安装器会自动创建分区,默认使用 LVM,根分区大小取决于磁盘容量和自动配置策略。这种自动方案适合大多数临时场景,但我个人在部署正式服务器时更倾向手动分区,因为这样可以精确控制 /boot 大小、给独立数据盘留出空间,甚至针对特殊场景调整 swap 大小。
手动分区的入口在安装目的地界面,选择磁盘后把“自动配置”改为“自定义”,然后按需创建挂载点。我一般在 x86_64 + UEFI 环境下使用这样一组分区方案:
| 挂载点 | 建议大小 | 文件系统 | 说明 |
|---|---|---|---|
| /boot/efi | 512MB | EFI System Partition | UEFI 固件必需的引导分区 |
| /boot | 1GB | xfs | 存放内核与 initramfs |
| / | 剩余空间或 50GB 起 | xfs | 根文件系统,RHEL 9 默认推荐 xfs |
| swap | 视内存而定 | swap | 内存不足时的交换空间 |
swap 大小的取值没有绝对标准。如果是内网测试机,内存足够大时可以干脆不分 swap;如果是生产服务器,通常建议按内存的 1 到 2 倍划分,但内存超过 16GB 之后继续成倍增加收益并不大,很多运维团队会固定给 16GB 或 32GB 的 swap 上限。RHEL 9 在手动分区界面还支持对 NVMe 盘、SSD 做对齐检查,一般默认设置即可,不需要额外操心。
如果磁盘上已经有旧系统或旧分区,可以在手动分区界面把旧分区逐个删除,再重新创建。删除分区前安装器会要求确认,强烈建议重要数据提前备份。RHEL 9 的安装器不会给你中途反悔的机会,一旦确认删除,分区表就真的改掉了。分完区之后,接受更改,回到安装信息摘要页面。
3.3 软件选择与root/用户配置
安装信息摘要页面的“软件选择”项,默认是“带 GUI 的服务器”,会安装 GNOME 桌面、图形管理工具等一系列图形化组件。如果这台机器是纯服务器,我建议直接改成“服务器”,只保留最核心的基础系统和命令行工具;如果只是测试环境、或者需要图形界面便于快速操作,就保留默认的带 GUI 项。选择结果直接影响安装时长和磁盘占用,带 GUI 的软件包数量远超命令行版。
接下来是 root 密码和创建用户。RHEL 9 默认要求 root 密码必须满足一定强度,如果设置得太简单,安装器会给出“密码过弱”的提示,但允许强制继续。生产环境不要贪图方便,root 密码建议用 16 位以上混合字符。同时我建议一定要创建一个普通用户账号,把它加入 wheel 组之后就能正常使用 sudo,日常运维完全没必要一直开着 root 终端。
网络和主机名的配置也在安装信息摘要页面。如果目标环境是 DHCP,装完就能自动获得 IP;如果是静态 IP 环境,建议在安装阶段就把 IP、网关、DNS 配好,避免进系统之后再折腾 nmcli 命令行。RHEL 9 的网络管理默认基于 NetworkManager,“网络和主机名”里直接设置即可,支持图形化填写,比在纯命令行里配要直观很多。
3.4 开始安装与首次启动
确认所有配置项都已完成,“开始安装”按钮从灰色变成可点击状态,就可以正式安装了。安装过程中左侧会有进度列表,包括写入文件系统、安装引导程序、执行自定义脚本等环节。RHEL 9 的 DVD 安装整体速度取决于磁盘和 CPU 性能,对普通 SATA 盘或虚拟机的虚拟磁盘来说,十几分钟到半小时都算正常,NVMe 固态盘会明显更快。
安装完成后系统提示重启。这里有个容易忽略的细节:虚拟机要在重启前把光驱里的 ISO 连接断开,或者把启动顺序改回硬盘优先,物理机则要拔掉 U 盘,否则重启后又会进入安装界面,白白等一轮。第一次启动进入系统后,会显示初始化欢迎界面,包括接受许可证、配置订阅等选项。这部分在离线环境里直接跳过订阅相关设置,先进入系统,随后再配置本地仓库。
4. 装完之后最容易被忽略的一件事:把DVD ISO变成本地仓库
4.1 为什么每个RHEL 9用户都需要一个本地repo
很多人在安装阶段就止步了,进系统之后才发现 dnf install 软件包时要么提示没有可用软件包,要么一直卡在查找镜像源。原因很简单:RHEL 9 默认的 /etc/yum.repos.d/redhat.repo 指向红帽 CDN,而离线环境访问不了外网。更麻烦的是,如果安装阶段本身就连不上网,系统交付时几乎是没有任何可用软件源的裸机状态。
这时候 DVD ISO 的价值就彻底体现出来了——它本身就带了一套完整的软件仓库。RHEL 9 的 DVD 镜像包含 BaseOS 和 AppStream 两个主要仓库,分别提供核心运行时基础组件和应用流软件。把镜像挂载到系统里,再把这些仓库指向本地挂载点,就能用 dnf 安装出很多常用软件。对没有订阅的内网环境来说,这是最直接、也是最稳妥的软件获取方式,不依赖外网,也不涉及任何绕过授权的操作。
4.2 挂载ISO并配置BaseOS/AppStream仓库
把 DVD ISO 变成本地仓库,核心就两步:挂载镜像,然后写 repo 配置。先创建挂载点并挂载镜像:
bash复制sudo mkdir -p /mnt/rhel9
sudo mount -o loop /path/to/rhel-9.3-x86_64-dvd.iso /mnt/rhel9
挂载完成后,在 /mnt/rhel9 下你会看到 BaseOS、AppStream 这两个关键目录。接下来在 /etc/yum.repos.d/ 里新建一个本地仓库配置文件,比如 rhel9-local.repo,内容如下:
ini复制[BaseOS-local]
name=RHEL 9 BaseOS Local Repository
baseurl=file:///mnt/rhel9/BaseOS
enabled=1
gpgcheck=0
[AppStream-local]
name=RHEL 9 AppStream Local Repository
baseurl=file:///mnt/rhel9/AppStream
enabled=1
gpgcheck=0
这里 gpgcheck 设成 0 是因为本地镜像已经经过红帽签名校验,离线环境使用重点在包可用性。如果你对内网安全性要求极高,也可以保留 gpgcheck=1 并指定镜像里的 RPM-GPG-KEY-redhat-release 作为 gpgkey,但配置会复杂一些。实际操作里,大多数内网环境都直接设 gpgcheck=0,只要确保镜像来源可靠就行。
配好后清理缓存并验证仓库:
bash复制sudo dnf clean all
sudo dnf repolist
在 repolist 输出里能看到 BaseOS-local 和 AppStream-local 两个仓库,并且包数量不为 0,说明本地源已经成功启用。
如果希望重启后依然自动挂载,把挂载项写进 /etc/fstab。假设 ISO 文件固定存放在系统某个路径下,可以这样加一行:
bash复制/path/to/rhel-9.3-x86_64-dvd.iso /mnt/rhel9 iso9660 loop,ro 0 0
注意这里设备路径必须写绝对路径。如果你的 ISO 文件放在 U 盘或外部移动盘上,还需要考虑设备在重启后的盘符变化问题。这种情况下建议用 UUID 替代设备路径,否则重启后可能挂载不上,导致 dnf 直接报错。
4.3 离线安装软件包的实战验证
仓库配置完成之后,就可以实际体验一下离线安装。比如安装 httpd 和 Python 3 开发工具:
bash复制sudo dnf install -y httpd python3-devel
只要 DVD 镜像里包含这些包,dnf 会直接从本地源解析并安装。安装过程中如果遇到依赖问题,通常是因为某些依赖只存在于仓库里的另一个模块流中。此时可以先用 dnf provides 或 dnf info 查一下包的具体来源,再针对性安装依赖。
RHEL 9 的 AppStream 仓库使用模块流机制,同一个软件可能会有多个版本流,比如 PostgreSQL 有 13、15、16 等不同版本流,默认启用的是其中一个特定版本。如果安装时有明确的版本要求,可以在包名后面加 @模块流,例如:
bash复制sudo dnf install -y postgresql@16
这个功能在离线环境里同样生效,对有版本强制要求的场景非常有用。需要说明的是,DVD ISO 里的仓库内容和红帽 CDN 在线仓库不是完全一致的,部分最新小版本更新补丁可能不在 ISO 中,但对搭建一套可用的基础系统来说已经完全够用。如果后续需要更新,再想办法接入可用的在线源或者定期用新版本 ISO 替换挂载即可。
5. 常见问题与排查实录
5.1 安装器不识别U盘/ISO引导失败
这是我遇到得最多的一类问题。U 盘启动后黑屏、卡在引导界面或提示无法找到安装介质,常见原因有这么几个。第一,写盘方式不对,比如直接把 ISO 解压到了 U 盘而不是写入镜像,这种情况引导程序根本没有被正确写进 U 盘。第二,启动模式不对,RHEL 9 的 ISO 同时支持 UEFI 和传统 BIOS,但有些服务器默认只开了 UEFI,如果你的 U 盘写盘方式与固件模式不匹配,也起不来。第三,U 盘本身质量不好或者 USB 口供电不足,导致读盘不稳定,换个后置 USB 口或者换一块 U 盘往往就能解决。
在物理机上遇到引导失败,建议先用启动参数进入 dracut shell 检查设备,用 ls /dev/disk/by-label 看能否识别到带 RHEL 标志的设备。如果识别不到,多半是存储驱动没有加载,需要在启动参数里追加 inst.dd 手动加载驱动,或者换一个写盘工具重新制作 U 盘。这类问题在部分新服务器带 NVMe RAID 控制器的环境里尤其常见,提前准备好驱动包会省很多事。
5.2 仓库配置完了还是装不上包
装完系统配置好本地仓库,执行 dnf install 却提示找不到软件包,这个看似简单的问题实际有几个隐藏原因。最常见的是 repo 文件里 baseurl 路径拼写错误,比如把 /mnt/rhel9/BaseOS 写成了 /mnt/rhel9/baseos,Linux 路径是大小写敏感的,任何大小写错误都会导致找不到仓库。其次,挂载可能没生效或者挂载点里根本没有对应目录,可以先 ls /mnt/rhel9 确认一下目录结构。
还有一种典型情况是 dnf 缓存了旧的仓库元数据,即使路径已经改对,也可能因为缓存问题一直报错。这时 dnf clean all 之后再重新 dnf makecache 就能解决。如果仓库列表里显示某个仓库处于“禁用”状态,检查 repo 文件的 enabled=1 是否写对。RHEL 9 还有一个特性:部分仓库会通过 include 或 exclude 过滤特定包,如果你发现某个包明确存在于 ISO 里但 dnf 就是搜不到,可以用 dnf list --showduplicates 排查是不是被版本或模块流过滤了。
5.3 密钥过期、订阅与模块流冲突
RHEL 9 在使用 dnf 时如果碰到订阅相关的报错,通常是因为系统尝试访问红帽 CDN 仓库但当前没有有效订阅或网络不通。内网环境里最干净的做法是把系统自带的 redhat.repo 屏蔽掉,或者至少把 enabled 置为 0,只保留本地 repo,避免 dnf 反复去访问不可达的网络源。千万不要随手删掉 /etc/pki/rpm-gpg 里的密钥文件,宁可配置 gpgcheck=0,也别手动去折腾密钥导入导出,搞不好会影响以后从其他受信任源安装软件。
模块流冲突在 RHEL 9 里也比较常见。例如启用了 PostgreSQL 16 模块流之后,再安装某个依赖特定版本 PostgreSQL 的软件包时,dnf 可能会提示模块流冲突。排查思路是先看当前启用的是哪个模块流:
bash复制dnf module list
如果默认模块流和实际需求冲突,可以先重置模块再启用目标版本,命令类似 dnf module reset postgresql 之后再 dnf module enable postgresql:16。这样操作完再安装依赖包就会顺畅很多。模块流机制是 RHEL 9 的一个亮点,但也确实是新手最容易绕晕的地方,遇到相关报错,别急着搜“为什么装不上”,先看一眼模块列表往往就有答案了。
一点个人经验收尾
我在实际部署里踩过最深的坑,不是安装界面操作,而是安装完成后习惯性地忘了处理本地仓库这件事。进了系统直接 dnf install,结果卡在网络源上半天,最后又回头重新挂 ISO、写 repo。这篇文章写了这么多,核心就是想强调:如果你照着这套流程走,安装完成、重启进入系统之后的第一件事,不要急着装任何软件,先把 ISO 挂载好、仓库配置好,一次性把基础环境理顺。
还有一个小技巧是保留安装用的 ISO 文件本身,不要装完系统就把它删掉。放在服务器硬盘或者 NAS 存储里,以后要装新软件、重建环境、甚至批量做相同配置的虚拟机,都可以继续复用这份离线源。真到了没有外网的现场,看着 dnf 从本地仓库嗖嗖地装包,你会特别庆幸当初留了这个后手。如果你刚开始接触 RHEL 9,就从这次离线安装开始折腾吧,这套流程走通一次,后面很多服务器安装和软件部署的活儿都会顺很多。
