You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ubuntu 22.04下适配systemd-resolve到resolvectl后无法上网的问题求助

Ubuntu 22.04下适配systemd-resolve到resolvectl后无法上网的问题求助

问题背景

我把Ubuntu升级到22.04后,用来路由工作VPN流量的脚本出问题了——原来脚本里用的systemd-resolve命令在22.04里被resolvectl替代了。

我的使用流程是:手动执行vpn.sh连接VPN,这个脚本会调用vpn_routes.sh(就是出问题的那个),让客户的特定在线工具流量走VPN,其他流量直接走外网。

我试了两种适配方案,但都会导致VPN连接成功后无法上网:

  1. 给resolvectl加软链接到systemd-resolve:
    sudo ln -s /usr/bin/resolvectl /usr/bin/systemd-resolve
    
  2. 直接把命令改成resolvectl:
    sudo resolvectl dns gxxx 11.xxx.x.xx 22.xxx.x.xxx
    sudo resolvectl domain xxxxx.com
    

原systemd-resolve命令是:

sudo systemd-resolve --interface gxxx --set-dns 11.xxx.x.xx --set-dns 22.xxx.x.xxx --set-domain xxxxx.com

完整的vpn_routes.sh脚本:

#!/bin/bash

GW=$(route -n | grep gxxx | grep 0.0.0.0 | awk '{print $2}')

echo "Gateway: ${GW}"

sudo route del -net 0.0.0.0 dev gxxx

sudo route add -net xx.x.xx.x gw ${GW} netmask 255.255.254.0 dev gxxx

sudo route add -net xx.x.xx.0 gw ${GW} netmask 255.255.254.0 dev gxxx

sudo systemd-resolve --interface gxxx --set-dns 11.xxx.x.xx --set-dns 22.xxx.x.xxx --set-domain xxxxx.com

补充网络状态信息(已脱敏)

执行ip a的输出:

1: lo: <LOOPBACK,UP,LOWER_UP> mtu xxx qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/XXX scope host
valid_lft forever preferred_lft forever

2: wlpxxxxx: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu xxx qdisc noqueue state UP group default qlen 1000
link/ether 64:xx:xx:xx:xx:xx brd ff:ff:ff:ff:ff:ff
inet xxx.xxx.x.x/xx brd xxx.xxx.x.xx scope global dynamic noprefixroute wlpxxxxx
valid_lft 68xxxsec preferred_lft 68xxxsec
inet6 2803:xxxx:98c4:xxxx:xxxx:efc5:xxxx:xxxx/64 scope global temporary dynamic
valid_lft 58xxxxsec preferred_lft 6xxxxsec
inet6 2803:xxxx:xxxx:8853:xxxx:ee6d:xxxx:xxxx/64 scope global dynamic mngtmpaddr noprefixroute
valid_lft 114xxxxxsec preferred_lft 11xxxxxxsec
inet6 fe80::xxxx:xxxx:xxxxx:64d5/64 scope link noprefixroute
valid_lft forever preferred_lft forever

3: gxxx: <POINTOPOINT,MULTICAST,NOARP,UP,LOWER_UP> mtu xxxx xxxx xxxxx state UP group default qlen xxx
link/none
inet 10.xxx.xx.xxx/xx scope global gxxx
valid_lft forever preferred_lft forever

4: docker0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 1500 qdisc noqueue state DOWN group default
link/ether 02:xx:xx:xx:xx:xx brd ff:ff:ff:ff:ff:ff
inet 172.xx.x.x/xx brd 172.xx.xxx.xxx scope global docker0
valid_lft forever preferred_lft forever
inet6 xxxxxxxxxxx/64 scope link
valid_lft forever preferred_lft forever

27: br-xxxxxxxxxxx: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu xxxx qdisc noqueue state DOWN group default
link/ether 02:xx:xx:xx:xx:xx brd ff:ff:ff:ff:ff:ff
inet 172.xx.x.x/xx brd 172.xx.xxx.xxx scope global br-xxxxxxxxxxx
valid_lft forever preferred_lft forever
inet6 xxxxxxxxxxxxxx/64 scope link
valid_lft forever preferred_lft forever

执行ip route的输出(示例):

default via xxx.xxx.x.x dev wlpxxxxx proto dhcp metric 600
xxx.xxx.xx.xx/xx via xxx.xxx.x.x dev wlpxxxxx
xxx.xxx.xx.xx/xx via xxx.xxx.x.x dev wlpxxxxx
xxx.xxx.xx.xx/xx via xxx.xxx.x.x dev wlpxxxxx
xxx.xxx.xx.xx/xx dev wlpxxxxx scope link metric 1000
172.xx.x.x/xx dev docker0 proto kernel scope link src 172.17.0.1 linkdown
172.xx.x.x/xx dev br-xxxxxxxxxxx proto kernel scope link src 172.xx.x.x linkdown
xxx.xxx.xx.xx/xx dev wlpxxxxx proto kernel scope link src xxx.xxx.xx.x metric 600
xxx.xxx.xx.x/xx via xxx.xxx.x.x dev wlpxxxxx
xxx.xxx.xx.x/xx via xxx.xxx.x.x dev wlpxxxxx
10.x.xx.x/xx via 10.xxx.xx.xxx  dev gpd0
10.x.xx.x/xx via 10.xxx.xx.xxx  dev gpd0
10.xx.x.x/xx via 10.xxx.xx.xxx  dev gpd0

执行resolvectl status的输出:

Global
Protocols: -LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported
resolv.conf mode: foreign
Current DNS Server: 11.xxx.x.xx
DNS Servers: 11.xxx.x.xxx 22.xxx.x.xxx
DNS Domain: xxxxx.com

Link 2 (wlpxxxxx)
Current Scopes: DNS
Protocols: +DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported
DNS Servers: xxx.xxx.x.x fexxxxxxxxxx

Link 3 (gxxx)
Current Scopes: DNS
Protocols: +DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported
Current DNS Server: 11.xxx.x.xxx
DNS Servers: 11.xxx.x.xxx 22.xxx.x.xxx
DNS Domain: xxxxx.com

Link 4 (docker0)
Current Scopes: none
Protocols: -DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported

Link 27 (br-xxxxxxxxxxx)
Current Scopes: none
Protocols: -DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported

问题分析与解决方案

从你的resolvectl status输出能看出问题:VPN接口gxxx被设置了+DefaultRoute,这会让所有DNS请求都优先走VPN的DNS服务器,但你的VPN DNS大概率只能解析内部的xxxxx.com域名,外部域名解析失败,自然就无法上网了。

原systemd-resolve命令的作用是只为指定接口的特定域名绑定DNS服务器,换成resolvectl时需要注意语法细节:

正确的命令应该是:

sudo resolvectl dns gxxx 11.xxx.x.xx 22.xxx.x.xxx
sudo resolvectl domain gxxx '~xxxxx.com'

这里的~是关键——它表示只有xxxxx.com及其所有子域名的DNS请求才会使用gxxx接口的DNS服务器,其他域名依然用无线接口wlpxxxxx的DNS,这样就能同时兼顾内网工具和外网访问了。

修改后的完整vpn_routes.sh脚本:

#!/bin/bash

GW=$(route -n | grep gxxx | grep 0.0.0.0 | awk '{print $2}')

echo "Gateway: ${GW}"

sudo route del -net 0.0.0.0 dev gxxx

sudo route add -net xx.x.xx.x gw ${GW} netmask 255.255.254.0 dev gxxx

sudo route add -net xx.x.xx.0 gw ${GW} netmask 255.255.254.0 dev gxxx

# 替换为正确的resolvectl命令
sudo resolvectl dns gxxx 11.xxx.x.xx 22.xxx.x.xxx
sudo resolvectl domain gxxx '~xxxxx.com'

执行完脚本后,再用resolvectl status检查gxxx接口的DNS Domain应该显示为~xxxxx.com,并且DefaultRoute应该变为-,这样就能正常访问内外网了。

备注:内容来源于stack exchange,提问作者Naxxio

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.21 12:38:06