为内部网络覆盖BIND中的某些DNS条目


39

我有一个运行BIND的DNS服务器的内部网络,该服务器通过一个网关连接到Internet。我的域“ example.com”由外部DNS提供商管理。该域中的某些条目,例如“ host1.example.com”和“ host2.example.com”,以及顶级条目“ example.com”,都指向网关的公共IP地址。

我希望位于内部网络上的主机将“ host1.example.com”,“ host2.example.com”和“ example.com”解析为内部IP地址而不是网关的IP地址。其他主机(例如“ otherhost.example.com”)仍应由外部DNS提供商解析。

通过在BIND中为“ host1.example.com”和“ host2.example.com”定义两个单一条目区域,我成功地为host1和host2条目做到了这一点。但是,如果我为“ example.com”添加区域,则该域的所有查询都将由我的本地DNS服务器解析,例如,查询“ otherhost.example.com”将导致错误。

是否可以将BIND配置为仅覆盖域的某些条目,然后递归解决其余项?



1
“是否可以将BIND配置为仅覆盖域的某些条目?” 不,不是BIND。使用子域。
bortzmeyer

1
Unbound似乎完全符合我的要求,因此我将Alnitak的答复设置为可接受的答案。但是最后,我将遵循bortzmeyer的建议,而不是覆盖域条目。感谢所有的答复!
雷米·布兰克

1
Bind现在可以在响应策略区域中执行此操作。请参阅下面的答案。其他解决方案(例如“未绑定”)不能覆盖CNAME。使用“绑定”中的策略区域,您不必做子域。您可以随意覆盖单个记录。
弗洛林·安德烈

Answers:


18

最好的方法是通过绑定9.8.1或更高版本中的响应策略区域。它允许您覆盖任意区域中的单个记录(并且无需为此创建整个子域,只需创建要更改的单个记录),即可覆盖CNAME等。其他解决方案(例如,未绑定)不能覆盖CNAME 。

https://www.redpill-linpro.com/sysadvent/2015/12/08/dns-rpz.html


编辑:让我们正确地做到这一点。我将根据上面链接的教程记录我所做的事情。

我的操作系统是用于Raspberry Pi的Raspbian 4.4,但是该技术应该在Debian和Ubuntu上进行任何更改,或者在其他平台上进行最少的更改即可工作。

转到将绑定配置文件保存在系统上的位置-在此处/etc/bind。在其中创建一个包含db.rpz以下内容的文件:

$TTL 60
@            IN    SOA  localhost. root.localhost.  (
                          2015112501   ; serial
                          1h           ; refresh
                          30m          ; retry
                          1w           ; expiry
                          30m)         ; minimum
                   IN     NS    localhost.

localhost       A   127.0.0.1

www.some-website.com    A        127.0.0.1

www.other-website.com   CNAME    fake-hostname.com.

它有什么作用?

  • www.some-website.com使用伪造的地址覆盖IP地址127.0.0.1,从而有效地将该站点的所有流量发送到环回地址
  • 它将流量发送www.other-website.com到另一个名为fake-hostname.com

可以在此处使用的绑定区域文件中可能包含的所有内容。

要激活这些更改,还有几个步骤:

编辑named.conf.local并添加以下部分:

zone "rpz" {
  type master;
  file "/etc/bind/db.rpz";
};

上面链接的教程告诉您向其中添加更多内容,zone "rpz" { }但这在简单的设置中是不必要的-我在这里展示的是使其在本地解析器上运行的最低要求。

编辑named.conf.options并在该options { }部分的某处添加response-policy选项:

options {
  // bunch
  // of
  // stuff
  // please
  // ignore

  response-policy { zone "rpz"; };
}

现在重新启动Bind:

service bind9 restart

而已。域名服务器现在应该开始覆盖这些记录。

如果需要进行更改,只需编辑db.rpz,然后再次重新启动Bind。

奖励:如果您想将DNS查询记录到syslog中,那么您可以密切注意程序,进行编辑named.conf.local并确保有一个logging包含以下语句的部分:

logging {
    // stuff
    // already
    // there

    channel my_syslog {
        syslog daemon;
        severity info;
    };
    category queries { my_syslog; };
};

重新启动再次绑定,仅此而已。

在运行Bind的计算机上对其进行测试:

dig @127.0.0.1 www.other-website.com. any

如果在其他计算机上运行dig,请使用@ the-ip-address-of-Bind-server而不是@ 127.0.0.1

我非常成功地使用了该技术,可以覆盖我正在工作的网站的CNAME,并将其发送到我刚刚测试的新AWS负载均衡器中。使用Raspberry Pi运行Bind,并且将RPi配置为充当WiFi路由器-因此,通过将设备连接到RPi上运行的SSID,我将获得测试所需的DNS替代。


1
请注意,BIND RPZ不能(实际上)基于每个QTYPE覆盖单个记录-它会覆盖特定所有者名称的所有记录。这意味着,如果要覆盖域的A记录而不是MX记录,则不能。您还必须将MX记录也放置在RPZ区域中,并使其与真实区域保持同步。
Alnitak

2
感谢您像您一样分解此内容。很有帮助。
sruffell

有什么警告吗?我正在尝试在pfsense上执行此操作,但是我无法“伪造”任何结果,它仍然报告真实地址。我相信我已经按照这封信的指示进行了。
Lenne

@Lenne应该可以了。我已经编辑了帖子,并添加了测试更改的建议。
Florin Andrei

@Lenne pfSense BIND软件包已经在GUI中内置了大约一年的时间,因此不需要配置。OP:可能值得一提的是您可以使用RPZ 进行的其他操作,例如使用NXDOMAIN进行答复或只是放弃响应。
miken32

21

未绑定的递归DNS服务器来覆盖各个资源记录的能力。

查看手册中的local-zonelocal-data配置设置,例如:

local-zone: "example.com." transparent
local-data: "foo.example.com. IN A 192.168.1.1"

transparent该设置local-zone告诉它不与任何供应名称做正常的递归查询local-data


1
似乎正是我想做的,谢谢。今晚我将阅读《 Unbound》。
雷米·布兰克

另一方面,它的智慧是值得怀疑的。拥有一个internal.example.com域将更加清晰。
bortzmeyer

@Bortzmeyer-你可能是对的,但我不认为Wouter只是为了好玩而把它放进去;-)
Alnitak

3
@bortzmeyer,有时别无选择。示例:SBS 2008必须具有单个LAN IP,但是仍需要使用路由器转发的外部IP从外部进行访问。Microsoft不允许在SBS上使用两个网卡,也不允许在同一卡上配置两个IP。如果本地服务器将DNS名称解析为外部IP,则路由器需要同时对LAN ip进行DNAT和SNAT,然后SBS上的日志将显示所有访问均来自路由器的IP,这是错误的。我将安装unbound在自己的路由器上,我认为解决方案要好得多。
Cosmin Prund

由于该问题特定于BIND,因此无法回答该问题。
bzeaman

4

您可能需要研究“ dnsmasq”,它可以通过调整分辨率来做一些非常聪明的事情。


谢谢,很好的提示。糟糕的dnsmasq不能进行递归解析,因此我仍然必须为此在另一个端口上运行BIND(我的ISP的DNS服务器是flakey)。
Remy Blank

4

您正在寻找的是拆分DNS,Webopedia将其定义为:

在拆分的DNS基础结构中,您为同一域创建两个区域,一个区域供内部网络使用,另一个区域供外部网络使用。拆分DNS将内部主机定向到内部域名服务器以进行名称解析,将外部主机定向到外部域名服务器以进行名称解析。

本质上,您将需要复制外部区域文件并将其支撑在内部DNS服务器上,然后更改或添加专门用于内部网络的记录。这是一个非常常见的设置,尽管要使两个DNS服务器之间的“外部”记录保持同步可能很麻烦。如果您在公用服务器上创建或更改记录,则还需要在专用服务器上创建或更改记录。

无论您使用哪种DNS服务器实施,都可以实施。在大多数设置中,您将有一台DNS服务器为外部网络服务,而另一台DNS服务器为内部网络服务。使用BIND(可能还有其他实现),可以通过在named.conf文件的zone部分中使用“ allow-query”语句在同一服务器上拥有该区域的两个版本。

BIND上的另一种可能性(并且我从未尝试过)是在内部DNS服务器上仅使用内部使用的记录来设置example.com域。然后,使用“ first”参数(与“ forwarders”一起)设置“ forward”语句。从理论上讲,这将向外部DNS服务器(如“转发器”中设置的)寻求答案,而该内部DNS服务器将没有您的内部记录并返回失败响应。然后,内部服务器会自行查看答案。确定这是否行得通,但这是一个想法。


使两个区域文件保持同步将很复杂,因为外部文件是通过动态DNS客户端更新的。不过,我将继续阅读forward语句。谢谢你的提示。
雷米·布兰克

不可以,BIND转发将不起作用,它仅适用于未知域,但是内部名称服务器将了解example.com,因此具有权威性。
bortzmeyer

1
如果我正确阅读了文档,则区域部分中的“ forward first”语句应告诉BIND出去,即使对于权威的本地域,也要在转发器中寻找答案,然后仅在可以的情况下使用本地信息。不能从货运代理那里得到答案。
贾斯汀·斯科特

如果您将全局设置为“转发优先”,“它将把查询发送给转发器,如果​​没有回答,将尝试回答查询”(来自doc),但是如果收到响应,它将不会尝试自行解决。如果您可以强制解决响应是否为权威性甚至是NXDOMAIN的问题,那将是很好的选择,但是如果从转发器得到响应,bind将不会尝试。
Pablo Martinez 2013年

3

在BIND中,我通过使用所需的主机名定义区域来获得此结果。如果您只想覆盖几个主机,则该方法很好。

我的区域声明如下所示:

zone "override.example.com" {
        type master;
        notify no;
        file "zone-config/override.example.com";
};

我的区域定义如下所示:

$TTL 4H
@       IN      SOA     ns.override.example.com.    root.override.example.com. (
                        2009072215      ; Serial
                        3600            ; Refresh
                        600             ; Retry
                        604800          ; Expire
                        3600    )       ; Minimum
;
                NS      ns
        IN      NS      ns.override.example.com.
        IN      A       192.168.1.100
ns      IN      A       192.168.1.100

因此,如果我在Intranet DNS和ISP DNS上查询example.com,我将获得相同的IP,但如果可访问Intranet DNS(主),则我将查询override.example.com,则结果将不同。


2

您已经走上了正确的轨道。

在内部DNS服务器上,您需要为紧邻“ example.com”下方的每个例外主机定义一个区域。为了最大程度地减少这些例外,通常的做法是将所有内部计算机命名为“ hosta.internal.example.com”,DNS服务器会将大多数查询发送到外部DNS服务器,但对“ internal.example.com”区域具有权威性。(一旦完成了一些小操作,通常会为“ internal.example.com”提供一对将客户端定向到的DNS服务器和一个将这些服务器定向到的单独的权威DNS。)

通常,只有当主机必须在内部和外部都可以访问时,才会创建您描述的异常。即使那样,您可能还是要从外部使用“ host1.example.com”,从内部使用“ host1.internal.example.com”。内部主机配置为在“ internal.example.com”中查找名称。在某些情况下,您已经在做的事情是适当的,例如,服务器证书将服务器标识为“ host1.example.com”,在这种情况下,您希望将其用作客户端连接的名称。


是的,对于“ host1.example.com”主机,它已经运行良好。棘手的部分是以相同的方式处理顶级“ example.com” ...
Remy Blank


2

事实上,还有另一种方法,即使可能略有不同。我有同样的情况,我有一个在外部和内部使用的域,并且有外部静态和动态主机。唯一真正痛苦的是外部动力。该解决方案可能不是最优雅的,但是可以通过一个小的脚本来实现。通常,我使用动态DNS提供程序的API来做自己的动态DNS脚本,我每5分钟通过cron运行一次此脚本:

1)获取我的外部IP。它改变了吗?没有出口。

2)更改IP,使用新的IP地址调用dyndns-provider的API,

3)使用外部IP sed db.mydomain.com

4)重启绑定。

对于我的家庭网络非常可靠地工作


我完成了相同的过程。请在我们的Wiki 隐形名称服务器中找到详细信息。但是无法dyn.dev.shahed.biz从World Wide 解决!您能帮我们解决这个问题吗?
沙希德·侯赛因
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.