本地DNS服务器方案对比
在搭建和完善HomeLab的过程中,有一个非常重要的服务就是DNS服务。本地DNS服务器负责解析本地域名,并转发上游DNS服务器的解析结果,是本地服务能正常访问的基石。本文介绍了自己搭建本地DNS服务器使用的几种方案,并简单对比了一下优缺点。
¶方案1 hosts文件
在进行DNS查询之前,会先检查一下hosts文件,如果有对应的记录,则直接返回结果。Windows系统的文件路径是C:\Windows\System32\drivers\etc\hosts,Linux系统是/etc/hosts。关于hosts文件更详细的介绍可以参考wiki百科。
这个方案最大的优点是简单。文件格式简单,修改起来很方便。如果要快速拉起一个服务,或者覆盖公共DNS服务器的结果,是一个不错的选择。
但是缺点也很明显,在某些场景下甚至是致命的。首先是只支持A、AAAA记录,无法添加txt、mx等其他类型的记录。假如要搭建一个邮箱服务,hosts文件完全无法支持。其次是只对本机有效,这意味着局域网内的其他机器无法通过域名的方式访问服务。
¶方案2 本机Windows运行bind服务
为了客服hosts无法添加A、AAAA记录的缺点,首先尝试了bind。bind是一款非常专业的DNS服务器,其详细介绍可以参考BIND 9 Administrator Reference Manual。
使用bind确实能添加其他类型的记录,但引入了更多的问题。首先,bind太专业了,导致维护起来太难了。如果遇到什么问题,解决起来也很麻烦。第二,需要手工修改网卡的DNS服务器地址。如果只有一两台设备还好,设备一旦多了,那将是灾难。第三,本机Windows不是服务器,不会24小时开机。如果休眠或关机,那么DNS指向此台电脑的设备将无法上网,又要修改网卡的DNS地址。非常麻烦。
这是一个非常不完美的解决方案,所以只使用的一小段时间,就迅速切换到了下一个方案。
¶方案3 路由器dnsmasq
bind的主要痛点是维护困难,不能24小时提供服务。而路由器里面的dnsmasq刚好能解决这两个问题。dnsmasq是一个轻量级的dns服务器软件,同时路由器又能满足24小时运行的要求,完美。详细的搭建过程可以参考搭建局域网DNS服务器。在路由器的设置中,将DNS服务器设置为路由器的IP地址,还能解决需要为每一台设备修改DNS服务器地址的问题。
此方案看起来非常完美,但实际使用的过程中,还是遇到了一些令人非常不爽的问题。首先,这个方案挑路由器,需要路由器提供追加dnsmasq配置文件的方法。如果是一些低端或运营商提供的路由器,很大概率是没有的。就需要更换路由器,或者刷机。
其次,路由器的地理位置是比较固定的,一般不会发生变化。但我的绝大多数服务是搭建在笔记本的一台VMware Linux虚拟机中,而且是桥接网卡。逢年过节回老家的时候,理论上依旧能访问这些服务,但需要经过一番折腾。老家的路由器没有本地域名的解析服务,需要想办法添加上。回到工作地点后,又要把这些临时设置的DNS记录又删除,着实麻烦。
最后,虚拟机之间通过域名访问,流量还需要走路由器,绕了一大圈,效率太低。
¶方案4 Linux服务器运行dnsmasq
此方案其实是对方案3的一个补充,和方案3同时使用。为了解决虚拟机之间通信走路由器的问题,我给每个虚拟机添加了两个网卡,一个NAT,一个桥接。这样每台虚拟机都有两个IP地址。其中一台开机自启动的Linux服务器部署DNS服务。如果DNS地址指向路由器,那么返回桥接网卡的IP地址,如果DNS地址指向Linux服务器,那么返回NAT网卡的IP地址。
只要将笔记本网卡的DNS地址指向Linux服务器,那么无论接入什么路由器,都能保证笔记本能解析本地域名。
方案3+方案4一直工作的很好,但遇到了NAT网卡IP地址变化导致无法访问的问题。桥接网卡在路由器设置了静态IP绑定,所以没有问题。NAT网卡虽然可以在VMware的DHCP配置文件设置静态IP地址,但如果在UI界面修改了其他的网络设置,配置文件会被覆盖,静态IP的配置就会丢失。也可以关闭VMware DHCP服务,在各个系统内部设置静态IP,就是太麻烦了。不同操作系统,甚至同一个操作系统的不同版本,设置方法都不同。不过还好,NAT网卡获取到的IP地址一般不会变化,暂时还能接受。
¶方案5 openwrt旁路由
VMware的DHCP服务没有一个很方便的查询IP地址的方法,所以每次IP变化后,都需要废很大的功夫才能确定新的IP地址。痛苦了几次后,终于受不了了,开始寻找新的方案。这个新的方案就是 openwrt 旁路由。
主路由关闭DHCP服务,由旁路由提供DHCP和DNS服务。同时通过DHCP选项,将网关设置为主路由,DNS设置为旁路由。当接入局域网的时候,所有参数会自动设置好,不再需要手工调整。同时openwrt提供了web界面,可以很方便的设置静态IP,查询DHCP分配的IP地址。更重要的是,此方案可以搭配任何主路由实现,只要主路由可以关闭DHCP服务。
主路由我通过树莓派3B刷入immortalwrt实现,而VMware的虚拟机网络则是直接安装了一个immortalwrt虚拟机,开机自启动。
这套方案非常完美。设置好之后维护成本很低,通过DHCP下发网卡参数,不再需要手工调整网卡参数。而且兼容性很好,无论是路由器网络还是虚拟机网络,都能很好适配。最后,openwrt是一个非常开放的系统,有很多软件包和插件可以折腾,扩展性拉满。
¶方案5.1 smartdns
dnsmasq向上游DNS查询时,总是返回最先查询到的结果,但不一定是访问最快的IP地址。所以就再引入了smartdns,对查询的结果做测速,返回访问最快的IP地址。smartdns专注于DNS查询缓存和测速,没有提供很完善的DNS记录设置,所以dnsmasq还是要保留。
smartdns监听53端口,向局域网提供DNS服务。dnsmasq监听5354端口,提供本地域名解析服务,作为smartdns的一个上游服务器。