简介

跨地区挂载一般使用 WebDAV(HTTPS) + Rclone,而同地区挂载为了速度和性能,NFS(Network File System,网络文件系统)是更好的选择。不过 NFS 自身不提供加密功能,在公网或能内网互通的机房上需通过 TLS 或 Kerberos 加密,也可以使用本文介绍的方法,利用 WireGuard 协议进行加密传输。

需要注意 WireGuard 协议通过 UDP 传输流量,部分服务商会对 UDP 进行 QoS,导致体验不佳。选择该方案前建议先使用 iperf3 测试 UDP 速度,确保服务商未作限制。

这里假设 VPS A 作为服务端存储数据,VPS B 作为客户端运行服务,通过 WireGuard 建立加密隧道,使 VPS B 能够安全地访问 VPS A 上的数据文件。以下操作演示环境为 Debian 12,默认以 root 用户进行。

配置 WireGuard

1. 安装 WireGuard

在两台 VPS 上都安装 WireGuard:

apt install wireguard

2. 生成密钥对

在两台 VPS 上分别生成 WireGuard 密钥对 private.key 和 public.key:

umask 077
wg genkey | tee /etc/wireguard/private.key | wg pubkey > /etc/wireguard/public.key
umask

3. 配置 WireGuard

我这里内网 IP 选择使用 10.0.1.0/24,VPS A(服务端)的 IP 设置为 10.0.1.1,VPS B(客户端)的 IP 设置为 10.0.1.2。你可以替换为其他网段或自己喜欢的保留地址。

a. 修改 VPS A(服务端)的配置文件 /etc/wireguard/wg0.conf:

[Interface]
Address = 10.0.1.1/24
ListenPort = 51820
PrivateKey = <VPS A 服务端私钥>

[Peer]
PublicKey = <VPS B 客户端公钥>
AllowedIPs = 10.0.1.2/32

# [Peer]
# PublicKey = <VPS C 客户端公钥>
# AllowedIPs = 10.0.1.3/32

b. 修改 VPS B(客户端)的配置文件 /etc/wireguard/wg0.conf:

[Interface]
Address = 10.0.1.2/24
PrivateKey = <VPS B 客户端私钥>

[Peer]
PublicKey = <VPS A 服务端公钥>
Endpoint = <VPS A 服务端公网 IP>:51820
AllowedIPs = 10.0.1.1/32
# PersistentKeepalive = 25

c. 在两台 VPS 上分别启动 WireGuard:

systemctl enable wg-quick@wg0.service
systemctl start wg-quick@wg0.service
systemctl status wg-quick@wg0.service

d. 检查是否连接成功:

wg show

运行上面命令后如果有流量数据或者能 ping 通对方说明可以正常通信,之后建议删除两台 VPS 上的密钥文件 /etc/wireguard/private.key。

* 如果 VPS A(服务端)上开启了防火墙,记得放行 WireGuard 端口给 VPS B(客户端),比如 ufw 防火墙:

ufw allow from <VPS B 公网 IP> to any port 51820

配置 NFS

NFS 服务端(VPS A)

a. 安装 NFS 服务端:

apt install nfs-kernel-server

b. 添加共享目录。编辑 /etc/exports 文件,假如这里要共享 /mnt/data/share 目录,文件最后添加:

/mnt/data/share 10.0.1.2(rw,sync,no_subtree_check,no_root_squash)

这表示将 /mnt/data/share 目录共享给 IP 地址为 10.0.1.2 的客户端。

其中:

  • rw: 文件权限。客户端拥有读写权限。
  • sync: 同步写入。写操作会立即写入磁盘,比 async 更安全,但稍慢。
  • no_subtree_check: 禁用子目录检查。禁用可以提高性能并避免某些权限错误。
  • no_root_squash: 不压缩 root 权限。客户端的 root 用户拥有服务端的 root 权限(安全性较低,一般用于信任的环境),默认是将客户端的 root 映射为匿名用户。

如果选择 root_squash 记得修改目录权限,保证客户端用户能正常读写。

应用配置更改:

exportfs -ra

c. 可选安全配置。确保 NFS 服务仅监听 WireGuard 接口,并且关闭 NFSv2 和 NFSv3,只使用 NFSv4。编辑 /etc/default/nfs-kernel-server,添加设置:

# 注释前面的 RPCMOUNTDOPTS 变量行,添加下面内容
RPCMOUNTDOPTS="--manage-gids -N 2 -N 3 -H 10.0.1.1"
RPCNFSDOPTS="-N 2 -N 3"

修改 /etc/nfs.conf:

[nfsd]
host=10.0.1.1

重启 NFS 服务:

systemctl restart nfs-kernel-server

* NFSv4 不需要 rpcbind 服务,可以禁用以避免不必要的启动和资源消耗:

systemctl mask rpcbind.service
systemctl mask rpcbind.socket

* 如果 VPS A(服务端)上开启了防火墙,记得放行 NFS 内网端口给 VPS B(客户端),比如 ufw 防火墙:

ufw allow from 10.0.1.2 to any port 2049
ufw allow from 10.0.1.2 to any port 111

NFS 客户端(VPS B)

a. 安装 NFS 客户端:

apt install nfs-common

b. 创建挂载点并挂载共享目录。假如这里要挂载到 /mnt/vps-a 目录:

mkdir -p /mnt/vps-a
mount -t nfs -o vers=4.2 10.0.1.1:/mnt/data/share /mnt/vps-a

现在,你可以尝试 ls /mnt/vps-a -l 查看 VPS A 上的共享文件了。

开机自动挂载

编辑 /etc/fstab 文件,添加以下行:

10.0.1.1:/mnt/data/share /mnt/vps-a nfs vers=4.2,x-systemd.requires=wg-quick@wg0.service 0 0

其中 x-systemd.requires=wg-quick@wg0.service 表示在尝试挂载这个文件系统之前,必须先成功启动 wg-quick@wg0.service 服务;0 0 这两个数字分别代表 dump 命令的备份频率和 fsck 命令的文件系统检查顺序。对于网络文件系统,通常设置为 0 0,表示不进行备份和检查。

至此,成功实现了在 VPS B 系统启动时自动挂载 NFS 文件系统,通过 WireGuard 加密隧道访问另一台 VPS A 服务器上的共享文件。

  • 无标签
写评论...