resolv.conf被自动覆盖解决方法:彻底搞定NetworkManager和systemd-resolved改写的完整指南
很多 Linux 服务器运维人员都遇到过这个让人抓狂的问题:好不容易手动修改了 /etc/resolv.conf 配置了理想的 DNS 服务器,结果重启网络或者重启服务器后,发现 resolv.conf 又被自动改回去了。这种反复被覆盖的情况,不仅影响工作效率,还可能导致 DNS 解析异常,影响业务正常运行。
本文将深入剖析 resolv.conf 被自动覆盖的根本原因,并给出 4 种经过生产环境验证的解决方案,帮你彻底搞定 NetworkManager 和 systemd-resolved 改写 resolv.conf 的问题。
一、resolv.conf 被覆盖的根本原因
/etc/resolv.conf 被自动覆盖,通常不是 Linux 系统的"bug",而是现代 Linux 发行版(如 Ubuntu 18.04+、CentOS 8+、Debian 9+)引入的网络管理守护进程在"接管" DNS 配置。主要有两个"嫌疑犯":
1. NetworkManager 导致的覆盖
NetworkManager 是一个动态网络配置守护进程,广泛用于桌面和服务器环境。它的设计目标是自动管理网络连接,包括有线和无线网络的 DNS 配置。当 NetworkManager 运行时,它会根据当前网络连接自动生成 /etc/resolv.conf 的内容。
如果你手动修改了 resolv.conf,NetworkManager 可能会在以下情况下覆盖它:
- 网络重启(
systemctl restart NetworkManager) - 系统重启
- 网络连接断开后重新连接
- DHCP 租约续期
2. systemd-resolved 导致的覆盖
systemd-resolved 是 systemd 套件中的 DNS 解析服务,从 Ubuntu 16.04 开始引入,在 Ubuntu 18.04+ 和 CentOS 8+ 中默认启用。它的设计目标是提供统一的 DNS 解析接口,支持 DNS-over-TLS、DNSSEC 等高级特性。
当 systemd-resolved 运行时,它通常会将 /etc/resolv.conf 改为指向本地 stub resolver(通常是 127.0.0.53)的符号链接。这意味着你直接修改 resolv.conf 实际上修改的是符号链接指向的文件,而 systemd-resolved 会根据自己的配置重新生成这个文件。
3. 如何判断是哪个进程在搞鬼?
在动手修改之前,先判断一下你的系统到底是哪个进程在接管 DNS 配置。运行以下命令:
ls -l /etc/resolv.conf
根据输出结果判断:
- 如果显示
/etc/resolv.conf -> ../run/systemd/resolve/stub-resolv.conf或类似内容,说明 systemd-resolved 在起作用 - 如果显示普通文件(不是符号链接),但内容总是被改回,可能是 NetworkManager 在管理
- 如果显示
/etc/resolv.conf -> /run/systemd/resolve/resolv.conf,说明 systemd-resolved 将 resolv.conf 指向了它自己生成的上游 DNS 配置
另外,也可以检查相关服务状态:
systemctl status NetworkManager
systemctl status systemd-resolved
二、解决方案一:配置 NetworkManager 不管理 DNS
如果你确定是 NetworkManager 在覆盖 resolv.conf,最直接的方法是配置 NetworkManager 不要自动管理 DNS,而是使用你手动指定的 DNS 服务器。
方法 1:修改 NetworkManager 配置文件
编辑 NetworkManager 的主配置文件:
sudo vi /etc/NetworkManager/NetworkManager.conf
在 [main] 部分添加以下内容:
[main]
dns=none
rc-manager=unmanaged
解释一下这两个参数的作用:
dns=none:告诉 NetworkManager 不要管理 DNS 配置,也就是不要改动/etc/resolv.confrc-manager=unmanaged:告诉 NetworkManager 不要管理/etc/resolv.conf文件的创建和删除
修改完成后,重启 NetworkManager 服务:
sudo systemctl restart NetworkManager
现在你可以手动修改 /etc/resolv.conf 了,NetworkManager 不会再来干扰。
方法 2:针对特定网络连接禁用 DNS 管理
如果你不想全局禁用 NetworkManager 的 DNS 管理功能,也可以针对特定的网络连接(比如 eth0)禁用 DNS 管理。
首先,查看当前的网络连接列表:
nmcli connection show
找到你要配置的连接名称(比如 eth0),然后运行:
sudo nmcli connection modify eth0 ipv4.ignore-auto-dns yes
sudo nmcli connection modify eth0 ipv6.ignore-auto-dns yes
这两个命令的作用是:
ipv4.ignore-auto-dns yes:忽略 IPv4 的自动 DNS 配置(比如从 DHCP 获取的 DNS)ipv6.ignore-auto-dns yes:忽略 IPv6 的自动 DNS 配置
然后,手动指定 DNS 服务器:
sudo nmcli connection modify eth0 ipv4.dns "8.8.8.8 8.8.4.4"
最后,重新激活网络连接:
sudo nmcli connection up eth0
三、解决方案二:配置 systemd-resolved 正确使用上游 DNS
如果是 systemd-resolved 在接管 DNS 配置,那么正确的做法不是禁用 systemd-resolved,而是配置它使用你想要的上游 DNS 服务器。
方法 1:修改 systemd-resolved 配置文件
编辑 systemd-resolved 的配置文件:
sudo vi /etc/systemd/resolved.conf
取消注释并修改以下参数:
[Resolve]
DNS=8.8.8.8 8.8.4.4
Domains=~.
关键参数解释:
DNS=8.8.8.8 8.8.4.4:指定上游 DNS 服务器(这里用 Google DNS 作为示例,你可以换成阿里云 DNS223.5.5.5 223.6.6.6或腾讯云 DNS119.29.29.29)Domains=~.:表示所有域名的 DNS 查询都使用上面指定的 DNS 服务器
修改完成后,重启 systemd-resolved 服务:
sudo systemctl restart systemd-resolved
然后,检查 /etc/resolv.conf 的内容:
cat /etc/resolv.conf
四、解决方案三:使用 chattr +i 锁定 resolv.conf
如果你不想折腾 NetworkManager 或 systemd-resolved 的配置,还有一个简单粗暴的方法:使用 chattr +i 命令将 /etc/resolv.conf 设置为不可修改。
具体步骤:
1. 首先,手动修改 /etc/resolv.conf 配置你想要的 DNS 服务器:
sudo vi /etc/resolv.conf
添加以下内容(示例):
nameserver 8.8.8.8
nameserver 8.8.4.4
2. 然后,使用 chattr +i 命令将文件设置为不可修改:
sudo chattr +i /etc/resolv.conf
现在,任何进程(包括 NetworkManager 和 systemd-resolved)都无法修改 /etc/resolv.conf 了。即使重启系统,这个属性也会保留。
如果你以后需要修改 resolv.conf,必须先移除不可修改属性:
sudo chattr -i /etc/resolv.conf
五、解决方案四:将 resolv.conf 改为符号链接
如果你的系统使用 systemd-resolved,那么正确的做法不是直接修改 /etc/resolv.conf,而是将 /etc/resolv.conf 改为指向 systemd-resolved 生成的上游 DNS 配置文件的符号链接。
具体步骤:
1. 首先,备份原有的 /etc/resolv.conf:
sudo cp /etc/resolv.conf /etc/resolv.conf.backup
2. 删除原有的 /etc/resolv.conf:
sudo rm /etc/resolv.conf
3. 创建正确的符号链接:
sudo ln -s /run/systemd/resolve/resolv.conf /etc/resolv.conf
4. 验证配置:
ls -l /etc/resolv.conf
cat /etc/resolv.conf
六、生产环境最佳实践
- 传统服务器,不需要动态 DNS:推荐使用
chattr +i方法,简单粗暴且有效 - 使用 systemd-resolved,希望正确集成:推荐使用方法四(符号链接)
- 使用 NetworkManager,需要针对特定网络连接配置 DNS:推荐使用方法一中的针对特定连接配置的方法
七、总结
resolv.conf 被自动覆盖是 Linux 服务器运维中的经典问题,根本原因通常是 NetworkManager 或 systemd-resolved 在自动管理 DNS 配置。本文介绍了 4 种解决方案,根据你的实际场景选择合适的解决方案,可以彻底解决 resolv.conf 被自动覆盖的问题。
内链推荐:
版权声明
本文仅代表个人观点。
本文系AI辅助作者原创,未经许可,转载请保留原文链接。

发表评论