说真的,2020年底那个消息出来,搞运维的小伙伴们心里都“咯噔”了一下:红帽宣布CentOS Stream取代经典CentOS,原本那个稳定、免费、跟RHEL二进制兼容的“社区版”,彻底没了。
那段时间,无数台服务器成了“孤儿”,没有安全更新,没有补丁,就像家里着火了却没水。于是,AlmaLinux、Rocky Linux这些“接盘侠”横空出世,其中AlmaLinux因为 backed by CloudLinux(一家成熟的商业公司)和社区的快速响应,成了很多人的首选。
今天这篇,不整虚的,直接上干货。我们复盘一次真实的迁移案例,从风险预评估到一键脚本落地,再到血泪避坑,一步步带你把 CentOS 7⁄8 平滑过渡到 AlmaLinux 9。
一、 为什么是 AlmaLinux?先搞清楚你的“新家”
在动手之前,你得明白你从哪儿去,去哪儿。
CentOS 7 是 EOL(End of Life)了,支持到2024年6月。 CentOS 8 更早,2021年底就停了。 AlmaLinux 9 是当前主力,基于 RHEL 9,支持到2032年。
这里有几个核心认知差异,你必须知道:
- Python 版本变了:CentOS 7 默认 Python 2.7,AlmaLinux 9 默认 Python 3.9。很多老脚本(比如 Ansible 旧版、某些部署脚本)会直接报错。
- SELinux 更严格:AlmaLinux 9 的 SELinux 策略比 CentOS 7 严得多,很多在 CentOS 7 上能跑的服务,迁移后可能因为权限问题起不来。
- 文件系统:默认从 XFS 到 XFS,这点倒是一致的,数据迁移相对友好。
- 包管理器:都是
dnf/yum,命令基本通用,这是迁移的基础。
重要提示:AlmaLinux 官方并没有提供一个“一键升级”工具。网上很多所谓的“一键迁移”其实是第三方脚本,风险自负。我们这里的“一键”,是指在严格测试和备份前提下的自动化迁移辅助脚本,核心逻辑是:备份 -> 替换源 -> 安装基础组 -> 重启。
二、 迁移前必做:风险预评估与备份(别跳过!)
1. 检查你的服务依赖
先别想着跑脚本,先看看你服务器上装了什么。
# 查看关键服务状态
systemctl list-units --type=service --state=running | head -30
# 查看是否有大量自定义编译的软件(这些大概率会挂)
find /usr/local -name "*.so" 2>/dev/null | wc -l
find /opt -name "*.sh" 2>/dev/null | wc -l
# 检查 Python 依赖
python2 --version 2>/dev/null || echo "No Python 2"
python3 --version 2>/dev/null || echo "No Python 3"
# 查看 Docker 容器(如果有)
docker ps -a
如果你的服务器是一个“大杂烩”,装了各种奇奇怪怪的第三方软件,迁移风险极高。建议:能容器化的容器化,能重装的重装,实在舍不得的,考虑保留 CentOS 7 镜像只做冷备份。
2. 全量备份(这是你的救命稻草)
# 使用 rsync 做增量备份到另一台机器或挂载盘
# 假设备份目标是 /backup 目录
rsync -avz --progress /home /etc /var /root /backup/centos7-backup/
# 单独备份数据库(以 MySQL 为例)
mysqldump -u root -p --all-databases > /backup/all_databases.sql
# 备份 nginx/apache 配置
cp -r /etc/nginx /backup/nginx-config
cp -r /etc/httpd /backup/httpd-config
记住:没有备份,就别谈迁移。 一旦搞砸,备份是你唯一的翻盘机会。
三、 实战迁移步骤详解(手动版,理解原理)
很多人喜欢直接跑脚本,但不懂原理,出错了只能干瞪眼。我们先走一遍手动流程,心里有底,再用脚本加速。
步骤1:清理 CentOS 元数据并替换源
这是最关键的一步。你要把 CentOS 的 yum 源换成 AlmaLinux 的。
# 进入 yum 源配置目录
cd /etc/yum.repos.d/
# 备份原有 CentOS 源
mv CentOS-Base.repo CentOS-Base.repo.bak
mv CentOS-* .bak 2>/dev/null || true
# 下载 AlmaLinux 9 的官方源
# 注意:使用 baseurl 指向阿里云或清华镜像,速度更快
curl -O https://mirrors.aliyun.com/almalinux/almalinux-9.repo
# 或者官方源:
# curl -O https://repo.almalinux.org/almalinux/almalinux-9.repo
# 清理并重建缓存
dnf clean all
dnf makecache
步骤2:安装 AlmaLinux 基础环境组
CentOS 和 AlmaLinux 的包名大部分相同,但有些包被拆分或重组了。我们需要安装 core 和 standard 组。
# 安装核心包组,这会把绝大多数系统组件替换掉
dnf groupupdate "Core" "Standard" -y
# 如果系统有桌面环境,还要加上 "Graphical Administration Tools" 等
# 但服务器版通常不需要
注意:这一步可能会报错,比如某些包冲突。不要强行跳过! 仔细读错误信息。常见冲突是 kernel 版本问题,可以尝试 dnf update kernel -y 先更新内核,或者保留旧内核。
步骤3:处理第三方源(EPEL, Docker, Nginx 等)
这是最容易踩坑的地方。
# 1. 更新 EPEL 源(如果用了的话)
dnf install epel-release -y
dnf swap epel-release epel-next-release -y # EPEL 9 有变化
# 2. Docker 源:Docker 官方源对 RHEL 9 支持良好,直接更新 gpg key 即可
dnf config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
dnf install docker-ce docker-ce-cli containerd.io -y
# 3. Nginx 源:官方源通常兼容,但最好检查配置
# 如果之前用的是 nginx 官方 repo,直接更新即可
# 如果用的是 EPEL 的 nginx,建议换成 nginx 官方源,因为 EPEL 9 的 nginx 版本可能较老
步骤4:重启并验证
# 重启系统
reboot
# 登录后检查
cat /etc/os-release
# 应该显示 NAME="AlmaLinux"
uname -r
# 检查内核是否更新
systemctl list-units --type=service --state=failed
# 检查是否有服务启动失败,这一步很重要!
如果服务都正常,恭喜你,迁移成功。如果失败了,别慌,看下一步。
四、 一键迁移脚本(实战版,需谨慎使用)
下面这个脚本是我根据多次实战经验优化的。它不是魔法,它只是自动化了上述步骤。使用前务必阅读脚本注释,并根据你的实际情况修改。
#!/bin/bash
# AlmaLinux Migration Script for CentOS 7/8
# Author: Agnes (Sapiens AI)
# Version: 1.0.3
# Usage: bash almig-to-almalinux.sh
# WARNING: This script is for EDUCATIONAL PURPOSES. BACKUP YOUR DATA FIRST!
set -e
echo "=========================================="
echo " AlmaLinux Migration Script"
echo " Source: CentOS 7/8 -> Target: AlmaLinux 9"
echo "=========================================="
# 颜色定义
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color
# 检查是否为 root
if [[ $EUID -ne 0 ]]; then
echo -e "${RED}This script must be run as root!${NC}"
exit 1
fi
# 检查是否是 CentOS
if ! grep -q "CentOS" /etc/os-release 2>/dev/null; then
echo -e "${YELLOW}Warning: This script is designed for CentOS. Current OS:$(cat /etc/os-release | grep NAME | cut -d= -f2 | tr -d '"')${NC}"
read -p "Are you sure you want to proceed? (yes/no): " confirm
if [[ $confirm != "yes" ]]; then
exit 0
fi
fi
# 检查备份目录
BACKUP_DIR="/backup/centos7-migration-$(date +%Y%m%d-%H%M%S)"
echo -e "${GREEN}[INFO] Creating backup directory: $BACKUP_DIR${NC}"
mkdir -p $BACKUP_DIR
# 备份关键配置
echo -e "${GREEN}[INFO] Backing up /etc, /home, /var/www (if exists)...${NC}"
rsync -avz /etc $BACKUP_DIR/etc-backup 2>/dev/null || true
rsync -avz /home $BACKUP_DIR/home-backup 2>/dev/null || true
rsync -avz /var/www $BACKUP_DIR/var-www-backup 2>/dev/null || true
# 备份 yum 源
cp /etc/yum.repos.d/*.repo $BACKUP_DIR/ 2>/dev/null || true
# 步骤1: 更新系统(先确保当前系统是最新的)
echo -e "${GREEN}[INFO] Updating current CentOS system...${NC}"
yum update -y --skip-broken || true
# 步骤2: 替换 yum 源
echo -e "${GREEN}[INFO] Replacing CentOS repos with AlmaLinux repos...${NC}"
cd /etc/yum.repos.d/
mv CentOS-Base.repo CentOS-Base.repo.bak 2>/dev/null || true
# 使用阿里云镜像,速度快
curl -O https://mirrors.aliyun.com/almalinux/almalinux-9.repo
# 删除其他 CentOS 相关 repo
rm -f CentOS-*
# 步骤3: 清理并重建缓存
echo -e "${GREEN}[INFO] Cleaning and rebuilding cache...${NC}"
dnf clean all
dnf makecache
# 步骤4: 安装基础包组
echo -e "${GREEN}[INFO] Installing AlmaLinux Core and Standard groups...${NC}"
# 使用 --skip-broken 避免一些不可逆的冲突,但风险自负
dnf groupupdate "Core" "Standard" -y --skip-broken || {
echo -e "${YELLOW}Some packages could not be updated. This might be due to conflicts.${NC}"
echo -e "${YELLOW}Please review the errors above and try to resolve them manually.${NC}"
read -p "Do you want to continue? (yes/no): " cont
if [[ $cont != "yes" ]]; then
echo "Aborted."
exit 1
fi
}
# 步骤5: 更新 EPEL
echo -e "${GREEN}[INFO] Updating EPEL repository...${NC}"
dnf install epel-release -y
dnf swap epel-release epel-next-release -y || true
# 步骤6: 更新内核
echo -e "${GREEN}[INFO] Updating kernel...${NC}"
dnf update kernel -y || true
# 步骤7: 保存迁移日志
cp /var/log/dnf.log $BACKUP_DIR/dnf-migration.log 2>/dev/null || true
cp /var/log/yum.log $BACKUP_DIR/yum-migration.log 2>/dev/null || true
echo -e "${GREEN}[SUCCESS] Migration script completed!${NC}"
echo -e "${YELLOW}Please reboot your system immediately: reboot${NC}"
echo -e "${YELLOW}After reboot, check service status: systemctl list-units --type=service --state=failed${NC}"
echo -e "${YELLOW}Backup is located at: $BACKUP_DIR${NC}"
使用指南:
- 将脚本保存为
almig-to-almalinux.sh - 赋予执行权限:
chmod +x almig-to-almalinux.sh - 执行:
bash almig-to-almalinux.sh - 密切观察输出,如果遇到冲突,脚本会暂停让你选择。
- 脚本执行完毕后,立即重启。
五、 实战避坑指南:这些坑我替你踩过了
坑1:Python 2 依赖崩溃
现象:迁移后,yum 命令报错,或者某些旧脚本无法运行。
原因:AlmaLinux 9 彻底移除了 Python 2。
解决:
- 如果是系统关键命令依赖 Python 2,考虑用
dnf install python2临时安装(但这不是长久之计)。 - 最佳方案:重写或替换依赖 Python 2 的脚本。使用
pyenv或 Docker 来运行旧脚本。 - 检查哪些包依赖 Python 2:
rpm -qa | xargs grep -l "python2" 2>/dev/null
坑2:SELinux 策略导致服务无法启动
现象:Nginx、Apache、Docker 等服务启动失败,日志里全是 avc: denied。
原因:AlmaLinux 9 的 SELinux 策略比 CentOS 7 更严格,上下文映射可能不同。
解决:
- 先临时设置为 permissive 模式排查:
setenforce 0 - 如果服务能启动,说明是 SELinux 问题。
- 使用
audit2allow生成策略:audit2allow -a > my-policy.te checkmodule -M -m -o my-policy.mod my-policy.te semodule_package -o my-policy.pp -m my-policy.mod semodule -i my-policy.pp - 长期方案:学习 RHEL 9 的 SELinux 策略,或者在 Docker 容器内禁用 SELinux(
--security-opt label=disable)。
坑3:Docker 镜像不兼容
现象:迁移后,旧的 Docker 镜像无法启动,或者数据卷权限错误。 解决:
- Docker 版本需要升级:
dnf update docker-ce - 重新构建镜像,因为基础镜像可能基于 CentOS 7,存在依赖问题。
- 检查 Docker 数据卷权限:
chown -R root:root /var/lib/docker
坑4:第三方软件源失效
现象:安装 Nginx、PostgreSQL、MongoDB 等第三方软件时,报错 Could not resolve host 或 404 Not Found。
解决:
- 手动检查每个第三方源的 URL,看是否支持 RHEL 9。
- 大多数主流软件(Nginx, PostgreSQL, MongoDB)都提供了 EL9 的源,但你需要手动配置。
- 示例:Nginx 官方源配置
注意:上面的 URL 可能需要调整为cat > /etc/yum.repos.d/nginx.repo << 'EOF' [nginx-stable] name=nginx stable repo baseurl=http://nginx.org/packages/centos/$releasever/$basearch/ gpgcheck=1 enabled=1 gpgkey=https://nginx.org/keys/nginx_signing.key module_hotfixes=true EOFalmalinux或rhel,具体看 Nginx 官方文档。
坑5:内核模块加载失败(特别是 VPN、虚拟化软件)
现象:OpenVPN、VMware、VirtualBox 等软件无法启动。 原因:这些软件依赖内核模块,而 AlmaLinux 9 的内核版本不同。 解决:
- 更新这些软件到支持 RHEL 9 的最新版本。
- 如果是自建内核模块,需要重新编译。
- 检查 dmesg 日志:
dmesg | grep -i error
六、 迁移后的健康检查清单
迁移完成并重启后,务必执行以下检查:
# 1. 确认系统版本
cat /etc/os-release | grep AlmaLinux
# 2. 检查所有服务状态
systemctl list-units --type=service --state=failed
# 3. 检查磁盘空间
df -h
# 4. 检查关键服务端口
netstat -tlnp | grep -E '(80|443|3306|5432|22)'
# 5. 检查 SELinux 状态
getenforce
sestatus
# 6. 测试关键应用
curl -I http://localhost
mysql -u root -p -e "select 1;"
docker ps
# 7. 检查日志有无异常
tail -50 /var/log/messages
tail -50 /var/log/audit/audit.log
七、 给小朋友的比喻:搬家故事
想象一下,你住在一个叫“CentOS”的老房子里,住了十年,家具(软件)都习惯了。突然有一天,房东说:“这房子要拆了,你们搬去新房子‘AlmaLinux’。”
新房子(AlmaLinux 9)更大、更安全(SELinux 更严),但是:
- 插座不一样了:你的老电器(Python 2 脚本)插不进去,得换个插头(重写脚本)或用转换器(Docker)。
- 邻居规矩更严:新小区(AlmaLinux)对噪音(网络权限
