本文已参与「新人创作礼」活动,一起开启掘金创作之路。
本文结合实际场景,从零开始搭建内网 CoreDNS 服务器并完成配置 内网中物理机、虚拟机等设备较多,配置 hosts 文件太麻烦,因此想到利用一台设备搭建 DNS 服务器以解救 hosts 文件 由于之前没有搭建 DNS 服务器的经验,在 GitHub 上搜了一下后,选择了 CoreDNS
前言
以前内网都是通过 hosts 管理内网的域名解析,如果设备少还好说,设备多了后,逐个设备维护 hosts 文件非常不现实。 如果能够在内网搭建 DNS 服务器,并调整路由器的 DNS 实现内网域名解析,就能够省去 hosts 配置的时间。
本文实践环境网络拓扑图:
clone 源码,编译,测试
clone & make
本地 Golang 环境直接编译
CoreDNS 使用 Golang 开发,因此编译需要 Golang 环境。 clone 源码并编译
git clone https://github.com/coredns/coredns
cd coredns
make
如果网络环境访问 GitHub 有困难,可以使用 Gitee 提供的镜像源 coredns:
git clone https://gitee.com/mirrors/coredns.git
cd coredns
make
基于 Docker Golang 编译
同样,先 clone 项目到本地
git clone https://github.com/coredns/coredns
cd coredns
如果本地没有 Golang 环境,也可以直接用 Docker 拉一个 Golang 镜像编译,以下为官方文档给出的命令
docker run --rm -i -t -v $PWD:/v -w /v golang:1.12 make
考虑到网络环境的问题,国内用户建议指定环境变量 GOPROXY
docker run --rm -i -t -e GOPROXY="https://goproxy.cn" -v $PWD:/v -w /v golang:1.12 make
测试
编译完成后,项目目录下多了一个 40MB 的二进制可执行文件 coredns
pi@rpi4:~/CoreDNS$ ls -lh
total 40M
-rw-r--r-- 1 pi sudo 3.6K Mar 9 00:39 ADOPTERS.md
lrwxrwxrwx 1 pi sudo 26 Mar 9 00:39 CODE_OF_CONDUCT.md -> .github/CODE_OF_CONDUCT.md
-rw-r--r-- 1 pi sudo 2.4K Mar 9 00:39 CODEOWNERS
lrwxrwxrwx 1 pi sudo 23 Mar 9 00:39 CONTRIBUTING.md -> .github/CONTRIBUTING.md
drwxr-xr-x 4 pi sudo 4.0K Mar 9 00:39 core
-rwxr-xr-x 1 pi sudo 40M Mar 10 20:56 coredns
-rw-r--r-- 1 pi sudo 1.4K Mar 9 00:39 coredns.1.md
-rw-r--r-- 1 pi sudo 246 Mar 9 00:39 coredns.go
-rw-r--r-- 1 pi sudo 3.3K Mar 9 00:39 corefile.5.md
drwxr-xr-x 2 pi sudo 4.0K Mar 9 00:39 coremain
-rw-r--r-- 1 pi sudo 2.4K Mar 9 00:39 directives_generate.go
-rw-r--r-- 1 pi sudo 254 Mar 9 00:39 Dockerfile
-rw-r--r-- 1 pi sudo 2.2K Mar 9 00:39 go.mod
-rw-r--r-- 1 pi sudo 62K Mar 9 00:39 go.sum
-rw-r--r-- 1 pi sudo 6.6K Mar 9 00:39 GOVERNANCE.md
-rw-r--r-- 1 pi sudo 12K Mar 9 00:39 LICENSE
-rw-r--r-- 1 pi sudo 1.9K Mar 9 00:39 Makefile
-rw-r--r-- 1 pi sudo 1.6K Mar 9 00:39 Makefile.doc
-rw-r--r-- 1 pi sudo 1.7K Mar 9 00:39 Makefile.fuzz
-rw-r--r-- 1 pi sudo 7.0K Mar 9 00:39 Makefile.release
drwxr-xr-x 2 pi sudo 4.0K Mar 10 20:16 man
drwxr-xr-x 2 pi sudo 4.0K Mar 9 00:39 notes
-rw-r--r-- 1 pi sudo 1.7K Mar 9 00:39 owners_generate.go
drwxr-xr-x 2 pi sudo 4.0K Mar 9 00:39 pb
drwxr-xr-x 49 pi sudo 4.0K Mar 9 00:39 plugin
-rw-r--r-- 1 pi sudo 1.3K Mar 9 00:39 plugin.cfg
-rw-r--r-- 1 pi sudo 5.7K Mar 9 00:39 plugin.md
-rw-r--r-- 1 pi sudo 8.4K Mar 9 00:39 README.md
drwxr-xr-x 2 pi sudo 4.0K Mar 9 00:39 request
lrwxrwxrwx 1 pi sudo 19 Mar 9 00:39 SECURITY.md -> .github/SECURITY.md
drwxr-xr-x 2 pi sudo 4.0K Mar 9 00:39 test
运行 coredns 并监听 1053 端口,此时由于没有配置文件,只能验证 DNS 服务器是否工作
./coredns -dns.port 1053
使用 dig 命令验证 DNS 服务器运行状况
dig @localhost -p 1053 a whiami.expamle.org
输出结果:
; <<>> DiG 9.11.5-P4-5.1-Debian <<>> @localhost -p 1053 a whiami.expamle.org
; (2 servers found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 20349
;; flags: qr aa rd; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 3
;; WARNING: recursion requested but not available
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
; COOKIE: c1c711345e8fb2e2 (echoed)
;; QUESTION SECTION:
;whiami.expamle.org. IN A
;; ADDITIONAL SECTION:
whiami.expamle.org. 0 IN AAAA ::1
_udp.whiami.expamle.org. 0 IN SRV 0 0 13225 .
;; Query time: 0 msec
;; SERVER: ::1#1053(::1)
;; WHEN: Tue Mar 10 21:01:06 CST 2020
;; MSG SIZE rcvd: 147
没有解析结果,但是 DNS 服务器已经在工作了,接下来就需要配置域名解析。
域名解析配置
coredns 基本参数
pi@rpi4:~/CoreDNS$ ./coredns -h
Usage of ./coredns:
-conf string
Corefile to load (default "Corefile")
-dns.port string
Default port (default "53")
-pidfile string
Path to write pid file
-plugins
List installed plugins
-quiet
Quiet mode (no initialization output)
-version
Show version
| 参数 | 解释 |
|---|---|
| -conf | 指定配置文件(默认为当前目录的 Corefile) |
| -dns.port | 指定 DNS 服务监听端口 |
| -pidfile | 指定 pid 文件的存放路径 |
| -plugins | 列出已安装的插件 |
| -quiet | 不打印日志 |
| -version | 显示版本信息 |
创建配置文件
hello, world 配置
在 coredns 所在目录下,新建文件 Corefile,并写入以下内容:
.:1053 {
forward . 8.8.8.8:53
log
}
上面配置为监听 1053 端口,将所有域名解析请求转发到 8.8.8.8:53,保存后运行 coredns 并 dig 一下:
dig @localhost -p 1053 a www.baidu.com
输出结果:
; <<>> DiG 9.11.5-P4-5.1-Debian <<>> @localhost -p 1053 a www.baidu.com
; (2 servers found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 25306
;; flags: qr rd ra; QUERY: 1, ANSWER: 4, AUTHORITY: 0, ADDITIONAL: 1
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;www.baidu.com. IN A
;; ANSWER SECTION:
www.baidu.com. 259 IN CNAME www.a.shifen.com.
www.a.shifen.com. 237 IN CNAME www.wshifen.com.
www.wshifen.com. 157 IN A 104.193.88.123
www.wshifen.com. 157 IN A 104.193.88.77
;; Query time: 19 msec
;; SERVER: ::1#1053(::1)
;; WHEN: Tue Mar 10 22:20:20 CST 2020
;; MSG SIZE rcvd: 192
可以看到,域名解析成功了。
按照需求进行配置
网络拓扑图如下:
DNS 服务器将运行在 rpi4 / rpi4-wifi 上面,并给局域网中的每个 IP 配一个域名。
由于内网环境比较简单,不需要复杂的配置,所以选择使用 CoreDNS 的 hosts 插件,文档参考:hosts 插件官方文档
创建一个 hosts 风格的文件 /etc/coredns/hosts,并按照拓扑图配置,内网域名为 lo:
192.168.3.254 rpi4.lo
192.168.99.254 rpi4-wifi.lo
192.168.3.253 rpi3.lo
192.168.99.253 rpi3-wifi.lo
192.168.3.252 mix2.lo
192.168.3.233 sia.lo
192.168.3.200 hyper-sia.lo
192.168.3.201 hyper-tesla.lo
192.168.3.99 ws5200.lo
192.168.3.1 pro2.lo
创建一个 Corefile /etc/coredns/Corefile:
配置解释:
- 将所有
lo域名根据同一目录下的 hosts 文件解析 - 所有其他的域名转发到 DNS 服务器
202.96.128.86:53
lo:53 {
hosts /etc/coredns/hosts
log
}
.:53 {
forward . 202.96.128.86:53
log
}
配置完成后启动 coredns,由于使用 53 端口,需要 root 权限:
sudo coredns -conf /etc/coredns/Corefile
启动 coredns 并验证配置
验证内网域名解析
使用 dig 验证解析域名 sia.lo
dig @localhost a sia.lo
解析结果:
; <<>> DiG 9.11.5-P4-5.1-Debian <<>> @localhost sia.lo
; (2 servers found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 50021
;; flags: qr aa rd; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
; COOKIE: 2acae2295223fd2b (echoed)
;; QUESTION SECTION:
;sia.lo. IN A
;; ANSWER SECTION:
sia.lo. 3600 IN A 192.168.3.233
;; Query time: 0 msec
;; SERVER: ::1#53(::1)
;; WHEN: Wed Mar 11 00:06:05 CST 2020
;; MSG SIZE rcvd: 69
可以看到,内网域名 sia.lo 已被成功解析到 192.168.3.233
验证其他域名解析
使用 dig 验证解析域名 github.com
dig @localhost github.com
解析结果:
; <<>> DiG 9.11.5-P4-5.1-Debian <<>> @localhost github.com
; (2 servers found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 1439
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 8, ADDITIONAL: 12
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
; COOKIE: 36e32dedc12b437a (echoed)
;; QUESTION SECTION:
;github.com. IN A
;; ANSWER SECTION:
github.com. 600 IN A 13.250.177.223
;; AUTHORITY SECTION:
github.com. 333 IN NS ns-1283.awsdns-32.org.
github.com. 333 IN NS ns-421.awsdns-52.com.
github.com. 333 IN NS ns-520.awsdns-01.net.
github.com. 333 IN NS ns-1707.awsdns-21.co.uk.
github.com. 333 IN NS ns4.p16.dynect.net.
github.com. 333 IN NS ns2.p16.dynect.net.
github.com. 333 IN NS ns1.p16.dynect.net.
github.com. 333 IN NS ns3.p16.dynect.net.
;; ADDITIONAL SECTION:
ns-1283.awsdns-32.org. 172465 IN A 205.251.197.3
ns-1707.awsdns-21.co.uk. 122490 IN A 205.251.198.171
ns-421.awsdns-52.com. 50849 IN A 205.251.193.165
ns-520.awsdns-01.net. 36645 IN A 205.251.194.8
ns1.p16.dynect.net. 80219 IN A 208.78.70.16
ns3.p16.dynect.net. 40730 IN A 208.78.71.16
ns4.p16.dynect.net. 77364 IN A 204.13.251.16
ns-1283.awsdns-32.org. 172314 IN AAAA 2600:9000:5305:300::1
ns-1707.awsdns-21.co.uk. 122491 IN AAAA 2600:9000:5306:ab00::1
ns-421.awsdns-52.com. 61826 IN AAAA 2600:9000:5301:a500::1
ns-520.awsdns-01.net. 35373 IN AAAA 2600:9000:5302:800::1
;; Query time: 5 msec
;; SERVER: ::1#53(::1)
;; WHEN: Wed Mar 11 00:09:40 CST 2020
;; MSG SIZE rcvd: 871
根据输出可见,非本地域名能够正常解析。 至此,coredns 配置完成。
修改路由器 DNS 配置或部署到公网
coredns 配置完毕后,需要将路由器 DNS 服务器指向配置好的 coredns。
但是一般家用路由器可能无法设置 IP 地址为内网的 DNS,因此我选择部署到自己的云服务器上,作为个人 DNS 服务器。
将 CoreDNS 作为服务 Service 运行
把 CoreDNS 作为 Service 运行,有助于我们管理进程。
以 Debian 系统为例,其他系统的 Service 可能有差异。
创建文件 /lib/systemd/system/coredns.service,本人目前对 Service 不太熟悉,因此配置从简:
[Unit]
After=network.target
[Service]
Type=simple
ExecStart=/usr/local/bin/coredns -conf /etc/coredns/Corefile -pidfile /var/run/coredns/coredns.pid
[Install]
Alias=coredns.service
启动服务并查看运行状况:
sudo systemctl start coredns
sudo systemctl status coredns
服务运行状况:
● coredns.service
Loaded: loaded (/lib/systemd/system/coredns.service; linked; vendor preset: enabled)
Active: active (running) since Wed 2020-03-11 00:44:45 CST; 3s ago
Main PID: 10987 (coredns)
Tasks: 11 (limit: 4546)
Memory: 5.0M
CGroup: /system.slice/coredns.service
└─10987 /usr/local/bin/coredns -conf /etc/coredns/Corefile -pidfile /var/run/coredns/coredns.pid
Mar 11 00:44:45 rpi4 systemd[1]: Started coredns.service.
Mar 11 00:44:45 rpi4 coredns[10987]: .:53
Mar 11 00:44:45 rpi4 coredns[10987]: lo.:53
Mar 11 00:44:45 rpi4 coredns[10987]: CoreDNS-1.6.7
Mar 11 00:44:45 rpi4 coredns[10987]: linux/arm64, go1.13.5, a64f0c75
设置自动启动:
sudo systemctl enable coredns
CoreDNS 服务配置完成。