如何在Vagrant集群中隔离节点并将master设为外网网关?
问题描述
嘿,我刚接触Vagrant,正尝试搭建一个包含入口节点master和两个slave节点的集群,拓扑结构如下:
-------- eth1 -------- eth0 | | 17.6.17.10 | internet ------->| master |-------| | | | slave1 | | | | | 17.6.17.2 | -------- | eth0 -------- 17.6.17.0/24 | eth0 -------- 17.6.17.3 | | |------------| slave2 | | | --------
我的当前Vagrantfile配置如下:
Vagrant.configure("2") do |config| config.vm.box = "generic/ubuntu1604" config.vm.define "master", primary: true do |master| master.vm.network "private_network", ip: "17.6.17.10" master.vm.hostname = "master" end config.vm.define "slave1" do |slave1| slave1.vm.network "private_network", ip: "17.6.17.2" slave1.vm.hostname = "slave1" end config.vm.define "slave2" do |slave2| slave2.vm.network "private_network", ip: "17.6.17.3" slave2.vm.hostname = "slave2" end end
现在三台机器都处于共享内网且能直接连接外网(因为默认的NAT网络),我希望隔离slave1和slave2,让它们无法直接访问外网,必须通过master作为网关才能访问,请问该怎么实现?
解决方案
没问题,咱们一步步来实现这个需求,核心是让master承担网关角色,关闭slave的直接外网访问,再配置转发规则:
1. 修改Vagrantfile调整网络配置
首先,我们需要调整每台机器的网络:
master保留默认的NAT网络(用来访问外网),同时保留现有的private_network作为内网接口。slave1和slave2禁用默认的NAT网络,只保留private_network,这样它们只能访问内网,无法直接连外网。
修改后的Vagrantfile如下:
Vagrant.configure("2") do |config| config.vm.box = "generic/ubuntu1604" # Master节点:保留NAT(默认)+ 内网private_network config.vm.define "master", primary: true do |master| master.vm.network "private_network", ip: "17.6.17.10" master.vm.hostname = "master" # 配置master启动时自动开启IP转发和iptables规则 master.vm.provision "shell", inline: <<-SHELL # 开启IP转发 echo "net.ipv4.ip_forward=1" >> /etc/sysctl.conf sysctl -p # 配置iptables SNAT规则,让slave通过master的NAT接口访问外网 iptables -t nat -A POSTROUTING -s 17.6.17.0/24 -o eth0 -j MASQUERADE # 保存iptables规则,重启后生效 iptables-save > /etc/iptables/rules.v4 # 确保iptables-persistent已安装(如果没装的话) apt-get update && apt-get install -y iptables-persistent SHELL end # Slave1:禁用默认NAT,只保留内网private_network config.vm.define "slave1" do |slave1| slave1.vm.network "private_network", ip: "17.6.17.2" slave1.vm.hostname = "slave1" # 禁用默认的NAT网络 slave1.vm.network "public_network", dev: "null", auto_config: false # 配置默认网关为master的内网IP,同时设置DNS slave1.vm.provision "shell", inline: <<-SHELL # 设置默认网关 ip route add default via 17.6.17.10 dev eth0 # 配置DNS(用谷歌DNS或者你喜欢的) echo "nameserver 8.8.8.8" >> /etc/resolv.conf SHELL end # Slave2:和slave1配置一致 config.vm.define "slave2" do |slave2| slave2.vm.network "private_network", ip: "17.6.17.3" slave2.vm.hostname = "slave2" # 禁用默认的NAT网络 slave2.vm.network "public_network", dev: "null", auto_config: false # 配置默认网关为master的内网IP,同时设置DNS slave2.vm.provision "shell", inline: <<-SHELL # 设置默认网关 ip route add default via 17.6.17.10 dev eth0 # 配置DNS(用谷歌DNS或者你喜欢的) echo "nameserver 8.8.8.8" >> /etc/resolv.conf SHELL end end
2. 关键配置说明
Master节点:
- 通过
sysctl开启IPv4转发,让Linux系统具备路由能力。 - 使用
iptables的MASQUERADE规则,把来自内网17.6.17.0/24的流量通过master的外网接口(eth0,也就是NAT接口)做地址转换,这样slave的流量就能通过master访问外网了。 - 安装
iptables-persistent来保存规则,避免重启后丢失。
- 通过
Slave节点:
- 通过
dev: "null"禁用默认的NAT网络,这样slave就没有直接的外网出口了。 - 设置默认网关为master的内网IP
17.6.17.10,让所有外网流量都发往master。 - 手动配置DNS,因为禁用NAT后slave可能没有自动获取到DNS服务器地址。
- 通过
3. 验证配置
启动所有机器后:
- 登录
slave1或slave2,执行ping google.com,如果能ping通,说明网关配置生效了。 - 执行
ip route,查看默认网关是否是17.6.17.10。 - 登录
master,执行iptables -t nat -L,能看到我们添加的POSTROUTING规则。
这样就实现了slave只能通过master访问外网的隔离效果啦!
内容的提问来源于stack exchange,提问作者Javier Benitez
相关产品推荐
相关产品推荐

