Исходный код CoreDNS основан на версии 1.3.1.
Архитектура
Архитектура CoreDNS реализована на основе фреймворка Caddy, весь проект использует множество подключаемых функций Caddy, общая структура кода относительно понятна и очень удобна для чтения.
Makefile
Сначала взгляните на часть Makefile кода CoreDNS:
Как видно из рисунка,core/plugin/zplugin.go
а такжеcore/dnsserver/zdirectives.go
файлы сделаныcoredns.go
пройти черезplugin.cfg
Сгенерировано. в,coredns.go
это файл запуска,plugin.cfg
представляет собой список настроенных плагинов, плагины по умолчанию следующие:
# Directives are registered in the order they should be
# executed.
#
# Ordering is VERY important. Every plugin will
# feel the effects of all other plugin below
# (after) them during a request, but they must not
# care what plugin above them are doing.
# How to rebuild with updated plugin configurations:
# Modify the list below and run `go gen && go build`
# The parser takes the input format of
# <plugin-name>:<package-name>
# Or
# <plugin-name>:<fully-qualified-package-name>
#
# External plugin example:
# log:github.com/coredns/coredns/plugin/log
# Local plugin example:
# log:log
metadata:metadata
tls:tls
reload:reload
nsid:nsid
root:root
bind:bind
debug:debug
trace:trace
health:health
pprof:pprof
prometheus:metrics
errors:errors
log:log
dnstap:dnstap
chaos:chaos
loadbalance:loadbalance
cache:cache
rewrite:rewrite
dnssec:dnssec
autopath:autopath
template:template
hosts:hosts
route53:route53
federation:federation
k8s_external:k8s_external
kubernetes:kubernetes
file:file
auto:auto
secondary:secondary
etcd:etcd
loop:loop
forward:forward
proxy:proxy
erratic:erratic
whoami:whoami
on:github.com/mholt/caddy/onevent
В код по умолчанию включены все существующие плагины, представленные в виде пары ключ-значение.
Посмотрите еще раз на файл запускаcoredns.go
:
Run
метод, но загруженныйgithub.com/coredns/coredns/core/plugin
Все методы инициализации в пакете.github.com/coredns/coredns/core/plugin
Только один в упаковкеzplugin.go
файл, и этот файл является файлом, сгенерированным Makefile, следующим образом:
// generated by directives_generate.go; DO NOT EDIT
package plugin
import (
// Include all plugins.
_ "github.com/coredns/coredns/plugin/auto"
_ "github.com/coredns/coredns/plugin/autopath"
_ "github.com/coredns/coredns/plugin/bind"
_ "github.com/coredns/coredns/plugin/cache"
_ "github.com/coredns/coredns/plugin/chaos"
_ "github.com/coredns/coredns/plugin/debug"
_ "github.com/coredns/coredns/plugin/dnssec"
_ "github.com/coredns/coredns/plugin/dnstap"
_ "github.com/coredns/coredns/plugin/erratic"
_ "github.com/coredns/coredns/plugin/errors"
_ "github.com/coredns/coredns/plugin/etcd"
_ "github.com/coredns/coredns/plugin/federation"
_ "github.com/coredns/coredns/plugin/file"
_ "github.com/coredns/coredns/plugin/forward"
_ "github.com/coredns/coredns/plugin/health"
_ "github.com/coredns/coredns/plugin/hosts"
_ "github.com/coredns/coredns/plugin/k8s_external"
_ "github.com/coredns/coredns/plugin/kubernetes"
_ "github.com/coredns/coredns/plugin/loadbalance"
_ "github.com/coredns/coredns/plugin/log"
_ "github.com/coredns/coredns/plugin/loop"
_ "github.com/coredns/coredns/plugin/metadata"
_ "github.com/coredns/coredns/plugin/metrics"
_ "github.com/coredns/coredns/plugin/nsid"
_ "github.com/coredns/coredns/plugin/pprof"
_ "github.com/coredns/coredns/plugin/proxy"
_ "github.com/coredns/coredns/plugin/reload"
_ "github.com/coredns/coredns/plugin/rewrite"
_ "github.com/coredns/coredns/plugin/root"
_ "github.com/coredns/coredns/plugin/route53"
_ "github.com/coredns/coredns/plugin/secondary"
_ "github.com/coredns/coredns/plugin/template"
_ "github.com/coredns/coredns/plugin/tls"
_ "github.com/coredns/coredns/plugin/trace"
_ "github.com/coredns/coredns/plugin/whoami"
_ "github.com/mholt/caddy/onevent"
)
Другой файл, сгенерированный Makefilezdirectives.go
следующим образом:
// generated by directives_generate.go; DO NOT EDIT
package dnsserver
// Directives are registered in the order they should be
// executed.
//
// Ordering is VERY important. Every plugin will
// feel the effects of all other plugin below
// (after) them during a request, but they must not
// care what plugin above them are doing.
var Directives = []string{
"metadata",
"tls",
"reload",
"nsid",
"root",
"bind",
"debug",
"trace",
"health",
"pprof",
"prometheus",
"errors",
"log",
"dnstap",
"chaos",
"loadbalance",
"cache",
"rewrite",
"dnssec",
"autopath",
"template",
"hosts",
"route53",
"federation",
"k8s_external",
"kubernetes",
"file",
"auto",
"secondary",
"etcd",
"loop",
"forward",
"proxy",
"erratic",
"whoami",
"on",
}
Два файла, один для загрузки всех подключаемых модулей и выполнения метода инициализации, другой для настройки массива.
назадzplugin.go
файл вgithub.com/coredns/coredns/plugin/auto
Взяв пакет в качестве примера, его соответствующий метод инициализации выглядит следующим образом:
Поэтому с помощью этого метода инициализации сгенерированные плагины по очереди регистрируются в caddy.
Инициализация CoreDNS
пройти черезRun
Метод входит в процесс инициализации CoreDNS.Run
Этот метод в основном заключается в проверке параметров, уделяя особое внимание пакету, который он вводит.github.com/coredns/coredns/core/dnsserver
, соответствующий метод инициализации выглядит следующим образом:
RegisterServerType
Метод завершает окончательную регистрацию плагина, где список плагиновDirectives
даcore/dnsserver/zdirectives.go
Содержимое файла содержит ряд информации о подключаемых модулях (порядок подключаемых модулей строго обязателен); иnewContext
то естьdnsContext
объект, который реализует интерфейс Caddy Context,пройти черезMakeServers
Завершите создание dnsServer.
Создание DNS-сервера
CoreDNS имеет множество вариантов создания серверов,
Существует несколько способов DNS, TLS, GRPC и HTTPS. Возьмем в качестве примера режим DNS, введитеNewServer
метод, основная функция которого заключается в добавленииpluginChain
Цепочка, которой соответствует соответствующий плагинplugin.Handler
метод обхода в обратном порядке,Предполагая, что загруженные плагины - это ошибки, лог и хост, после обратного порядка, так как плагины добавляются сзади на передhost-->log-->errors
, окончательный фактический порядок загрузкиerrors-->log-->host
, в том же порядке, как определено.
Выполнение плагина
Все плагины в основном реализуютHandler
интерфейс,
Name
Метод — это название плагина, сосредоточьтесь наServeDNS
метод.ServeDNS
Есть три параметра,Context
представляет весь контекст,ResponseWriter
Указывает, что сообщение возвращается клиенту,dns.Msg
по запросу клиента.Когда каждый плагин обрабатывает запрос, он вызывает
NextOrFailure
Метод вызывает следующий плагин для обработки соответствующей логики, то есть цепочек вызовов; вызовWriteMsg
Метод завершает вызов завершения, передавая сообщение клиенту.Если вам нужен пользовательский плагин, он в основном реализован
Name
а такжеServeDNS
метод, а вplugin.cfg
Очень удобно добавлять информацию о плагине в соответствующее место, чтобы завершить реализацию пользовательского плагина.
Плагин Kubernetes
Kubernetes также предоставляется в виде подключаемых модулей в CoreDNS, в основном предоставляя внутренние ресурсы в качестве источника разрешения доменных имен.
запускать
Как и другие подключаемые модули, Kubernetes также выполняет init для регистрации подключаемого модуля в caddy, а затем вызываетsetup
способ завершения работы по запуску. посмотриsetup
Главное что делать.
kubernetesParse
Разберите соответствующую конфигурацию подключаемого модуля Kubernetes, затем вызовитеInitKubeCache
инициализацияkubeClient
, во время вызоваnewdnsController
Инициализируйте dnsController, взаимодействуйте с кластером Kubernetes через dnsController и получите соответствующие данные в кластере; наконец, вызовитеAddPlugin
Добавьте плагин в конфигурацию в виде связанного списка для завершения инициализации.
бегать
бежать, чтобы достичьServeDNS
метод начинается. Главное — ввести разную логику обработки, разбирая разные типы запросов.
ServiceBackend
Завершите разрешение доменного имени.
Services
В основном в соответствии с конкретным типом запроса, получить все соответствующие услуги;Reverse
В основном выполняют действия по обратному разрешению доменного имени, то есть получают соответствующее доменное имя через IP;Lookup
В основном используется для поиска вышестоящего DNS-сервера;Records
В основном выполняют работу по разрешению доменных имен и возвращают определенные записи.Суммировать
Структура кода CoreDNS очень понятна: загрузив пользовательскую последовательность подключаемых модулей во время инициализации, они по очереди внедряются в caddy, а при выполнении выполняются последовательно в соответствии с определенной последовательностью подключаемых модулей, формируя Структура цепного вызова. Вся унифицированная структура кода формируется за счет создания DNSServer и персонализированной реализации нескольких подключаемых модулей.