Skip to content

内网静态 DNS 解析方案:libvirt dnsmasq 集中下发(虚拟机免配置)

适用场景:libvirt NAT 网络上的虚拟机需要用内网域名直连集群服务(如 Rancher server-url、agent 回连、节点注册),同时不影响宿主机/公网对同域名的正常访问。

1. 需求与方案对比

ai-ear.cn 为例:内网 K8s 集群希望 VM 把该域名解析到集群节点(192.168.122.20/21/22),公网用户仍解析到公网服务器。

方案优点缺点结论
逐台 VM 改 /etc/hosts简单直接每台都要改、新 VM 重复劳动、易遗漏弃用
libvirt dnsmasq 静态记录集中配置一次、所有 VM(含新建)自动生效、同名多 IP 轮询容错对宿主机本机也生效(需处理,见 §4)采用

2. 原理

  • libvirt NAT 网络自带的 dnsmasq(监听网关 192.168.122.1:53)是网络内所有 VM 的默认 DNS(DHCP 下发)。
  • dnsmasq 的 <host> 静态记录优先于上游转发:匹配域名返回内网 IP,其余域名正常转发公网解析。
  • virsh net-update 支持热更新--live)+ 持久化--config),无需重启虚拟网络(net-destroy 会中断所有 VM 网络,务必避免)。

3. 实施步骤

bash
# 在宿主机执行:ai-ear.cn → 3 个 control-plane 节点
for ip in 192.168.122.20 192.168.122.21 192.168.122.22; do
  virsh -c qemu:///system net-update default add dns-host \
    "<host ip='$ip'><hostname>ai-ear.cn</hostname></host>" --live --config
done

# 查看已配置记录
virsh -c qemu:///system net-dumpxml default | grep -A3 "<dns>"

dnsmasq 对同名多条记录轮询返回全部 IP,具备基础容错。

删除记录

bash
virsh -c qemu:///system net-update default delete dns-host \
  "<host ip='192.168.122.20'><hostname>ai-ear.cn</hostname></host>" --live --config

4. 关键坑:静态解析对宿主机本机同样生效

宿主机使用 systemd-resolved(127.0.0.53)时,域名查询会被转发到 virbr0 的 DNS(192.168.122.1),导致宿主机访问该域名也解析到内网——公网站点打不开、TLS 证书对不上。

修复:宿主机 /etc/hosts 固定公网 IP(nsswitch files 优先级高于 DNS,不影响 VM):

bash
sudo sh -c 'grep -q "^8.153.84.140 ai-ear.cn" /etc/hosts || echo "8.153.84.140 ai-ear.cn" >> /etc/hosts'

效果:宿主机走公网,VM 走内网,互不干扰。

5. 验证

bash
# VM 内:应解析到内网节点 IP
ssh root@192.168.122.20 'getent hosts ai-ear.cn'

# 宿主机:应解析到公网 IP
getent hosts ai-ear.cn        # 预期 8.153.84.140

6. 运维备查

操作命令
查看网络列表virsh -c qemu:///system net-list
查看 DNS 记录virsh -c qemu:///system net-dumpxml default | grep -A10 "<dns>"
添加记录virsh net-update default add dns-host "<host ip='IP'><hostname>NAME</hostname></host>" --live --config
删除记录virsh net-update default delete dns-host "<host ip='IP'><hostname>NAME</hostname></host>" --live --config
仅临时生效(重启失效)去掉 --config
仅写入配置(重启生效)去掉 --live

关联阅读:Rancher on RKE2 部署运维手册(内外网域名分离的完整应用案例)