记录使用BIND本地搭建DNS服务器的过程和遇到的问题及其解决方案,首先强推一个DNS教程,个人感觉写的很好。
UBUNTU14.04安装配置BIND
有两种安装方法,一种是下载源码编译安装,另一种是直接apt install
安装。建议使用apt比较方便。
sudo apt-get install bind9
网上有人翻译了一份BIND安装指南 上面有BIND的各种配置方法。
之后直接运行 sudo service bind9 start
就会在后台启动DNS域名服务器。但是我们还没有对这个服务器进行任何配置,接下来我就讲讲bind9中配置文件的结构和语法。
bind9 配置文件结构
如果你是apt install
安装的并且没有添加任何参数,那么bind9配置文件会默认被放在 /etc/bind
目录下。我们来看看这个目录默认有哪些文件:
named.conf
初步配置DNS服务器,我们只需要关注红框内的文件,其中最主要的是named.conf
这个文件,文件内容如下:
这个文件里只有三行include
,这里include的含义和C语言中的类似,声明了这个配置文件的内容由这三个include语句指向的文件内容组成。接下来我们分别看看这三个文件的内容。
named.conf.options
markdown-img-paste-20180301155236585.png这个文件配置的是bind的全局运行选项:
-
directory指定了缓存文件的存放目录,和本次实验没啥关系,保持默认值即可。
-
dnssec-validation是DNS安全相关的参数。同样保持默认值。
剩下两个默认的option也和本次实验没什么关系,因此不过多介绍。
named.conf.local
这个文件配置这个DNS服务器上的zone文件的位置和类型,我写好的named.conf.local如下:
markdown-img-paste-20180301221328117.png以第一项example.com
为例:
-
type: 指定本DNS服务器的类型。bind9共支持4种服务器类型:master server(主服务器)、caching server(缓存服务器)、slave server(从服务器)、混合模式服务器(既作为主服务器又有cache)。具体的type参数见此链接。
-
file: 指定这个zone(对本例来说就是"example.com"这个域名所管辖的zone)对应的zone file的位置,我们接下来就要在这个file选项指定的文件中写这个区的zone file。
name.conf.default-zones
这个文件的内容如下:
markdown-img-paste-20180301222457737.png从第一句注释可以看出这个文件的作用:存储根DNS服务器的信息,这个文件基本不用我们管,因为根DNS服务器的信息很少会变化。
zone file 写法
zone file 中存储当前域名所管辖的域中的所有资源记录(Resource Record),每条资源记录的格式如下:
NAME(域名) CLASS(网络类型,一般是IN:INTERNET) TYPE(记录类型) RDATA(记录值)
我们以named.conf.local中的第二项("jjw.com"的zone file:“db.jjw.com”)为例来描述zone file 的写法:
markdown-img-paste-20180301232127399.png-
$ORIGIN: 这个zone文件对应的域名。关于ORIGIN的作用,我感觉就是使得zone file更加简洁。它一般有两种用途:
-
被加载相对域名后面来构成绝对域名:比如上面的文件中的第一条A记录“233” ,实际上等价于绝对域名"233.jjw.com."。
-
被用来和@一起使用:@在zone file中有特殊含义,bind9解释zone file时,会将其中的@都替换成最后一个
markdown-img-paste-20180301225212259.png$ORIGIN
标识的域名,如果一个zone file中没有$ORIGIN
标识,那么bind9将会用named.conf.local
中配置的对应区域名来代替@标识:
-
在本例中,就是用jjw.com来替代。
-
$TTL:Time To Live,有效时间,即这个zonefile的有效时间,过了这个有效时间就要去权威服务器中请求更新zonefile,这里有效时间设置为604800秒,也就是18h。
-
SOA记录:这是每个zone file中最重要的一个记录,也是开头的第一条RR。它记录了这个域的授权信息,所谓“授权信息”指的就是当前这个域是由哪个权威服务器进行管理的,以及和这个权威服务器通讯的一些建议参数,SOA记录的格式如下:
jjw.com. IN SOA 本区中的权威域名服务器的域名 管理员邮件地址 (建议通信参数,详见上图注释)
-
NS记录:记录管理相应域名的信息的域名服务器。简单来说,如果有一个被请求解析的域名在本zone file中没有A记录,但是有一条NS记录,那么接下来服务器就会告诉请求者到这个NS记录指定的域名服务器中继续请求解析。
-
A记录:记录域名对应的IP地址
-
CNAME:记录域名对应的别名,本例中
www
是233.jjw.com
的别名。
zone file还有很多类型的RR,详见这个链接。
log 配置
bind9以后台服务的形式启动,因此运行过程中的解析过程不会很明显地显示。默认情况下,bind9服务器的日志信息会被linux系统日志程序syslogd记录在/var/log/messages
文件中,由于这个文件中还包括其他服务的日志信息,因此显得很乱,难以阅读。
为了更方便地筛选和查看DNS服务器的日志信息,需要配置bind9的日志文件来将服务器的日志从系统日志中提取出来。
查看/etc/apparmor.d/usr.sbin.named 来获取bind可访问的log文件夹
apparmor.d是ubuntu系统下实现强制权限管理的文件,里面记录了多个应用的权限信息。
文件内容如下:
markdown-img-paste-20180302103727104.png红框内的注释说明了下面那个文件夹是named用于记录自己的log的文件夹(你也可以改成其他的,需要root权限),这个文件夹将在我们下面的named.conf.log文件的书写中用到。
配置named.conf
仅需添加一行:
markdown-img-paste-2018030123380834.png配置named.conf.log
markdown-img-paste-2018030123412180.png简单说明一下这个logging配置,主要配置两个选项:channel和category
-
channel:定义一个bind日志文件的各种属性。
-
category:指定对应日志的标签,可以是上面定义的channel名。
一般按照上图这么写就行了,可以看到我们上一步得出的那个文件地址写在了file
参数的位置;还可能需要调整的是print-severity
这个参数。severity的定义如下:
简单来说,severity指定“log等级”,共有七个等级(如上图),从上到下等级递减,日志文件将会记录log等级大于或等于指定等级的日志信息。例如:上图配置中的severity指定为debug
,因此日志文件会记录上面六个等级的日志信息。一般情况下,severity设置为info
即可。
具体的log配置及其参数设置见这个链接。
运行BIND,用dig验证是否正常运作
启动bind9服务
使用命令
services bind9 start
修改/etc/resolv.conf
现在你已经在本机启动了DNS服务器,但是你的操作系统现在并不是以本机作为DNS服务器的,本机默认的DNS服务器记录在 /etc/resolv.conf中,我的电脑中默认内容是这样的:
markdown-img-paste-20180302113659121.png就是咱们学校的DNS服务器地址。在最前面添加一条本机ip(27.0.0.1),就会首先以本机IP指定的服务器来解析域名。(在做实验时,为了避免其它服务器的干扰,最好备份并删除这两个服务器记录,只留下本机IP)。
当然还有一种更方便的,不需要修改/etc/resolv.conf
方法:
@
后面的内容是指定此次查询使用的DNS服务器。更多dig命令的用法见此链接。
dig 测试
使用这个zone file:
markdown-img-paste-20180302133427336.pngdig测试结果如下;
-
dig emm1.jjw.com
在zone file 的定义中可以看到我们定义了一条CNAME记录,它将
markdown-img-paste-20180302133359706.pngemm1.jjw.com
的正式名称定义为emm.jjw.com
,因此dig到的信息如下,可以看到CNAME记录也被返回:
-
dig emm.jjw.com
这就是简单的A记录查询,下图中可以看到成功dig到了我们在zonefile中定义的
markdown-img-paste-20180302133306912.pngemm.jjw.com
的IP:
遇到的问题及解决方案
log配置写完后重启bind9服务失败
这是因为系统中目前并没有/var/log/named
文件夹,需要创建,使用命令:
sudo mkdir /var/log/named
还需要修改/var/log/named
的权限为bind可用,使用命令:
sudo chown bind:bind /var/log/named
用ls -l
命令查看是否修改成功:
这样的话,就可正常使用bind日志了,运行bind9服务期间关于bind9的信息都可以用下面这条命令查看:
cat /var/log/named/bind.log
named.conf.local 中没写权威服务器A记录报错
这个问题纠结了好久,问题是这样的:
用bind9配置DNS主服务器的时候,比如我写了这样一个zone file:
markdown-img-paste-20180302120724450.png经过测试,最后一行的域名服务器的A记录如果不写就不能成功dig到test.example.com的A记录;如果写了就可以。但是ns1的A记录是随意的IP地址(因为我是随意写的),所以这个A记录应该起不到什么实质作用。那么问题来了:为什么一定要在zonefile中写域名服务器的A记录才能够成功dig到其他子域名的A记录(即使这个A记录中的IP是任意的)?
下面是添加域名服务器的A记录后的dig结果:
markdown-img-paste-20180302120844650.png下面是不加域名服务器A记录的dig结果:
markdown-img-paste-20180302120906854.png经过查看bind的日志,发现不加域名服务器A记录时会出现如下error:
markdown-img-paste-20180302121037550.png这说明bind会检测这个zonefile的合法性,而如果不写权威域名服务器的A记录,那么在检查文件合法性的时候就会报错,导致解析失败。
那么为什么我随便写一个权威服务器的ip都能成功解析测试域名tests.example.com呢?
经过询问老师,我认为可以这样解释这个问题:
因为我本地这个dns服务器中有tests.example.com.的A记录,所以并不会去访问权威服务器ns1.example.com.
,因此在这种情况下那条A记录是无所谓写什么的。如果本机的zonefile中没有写tests.example.com.
的A记录,在开启递归查询的情况下,就会使用ns1.example.com.
的A记录继续向上询问权威服务器ns1.example.com.
。这时才会使用到这个ns1.example.com.
的A记录,就会导致域名解析失败。
关闭递归查询导致无法解析本服务器A记录之外的域名
如果在named.conf.option
中添加了这样的一行
那么就会关闭递归查询,此时就无法查询到除了本地DNS记录以外的的域名记录。
开启这个选项之后,请求解析 baidu.com
失败:
关闭这个选项之后,成功解析baidu.com
的IP:
网友评论