PowerDNS und PowerDNS-Admin installieren (AlmaLinux/CentOS)

Anleitung um den PowerDNS Authoritative Server zur Auflösung interner Namen zu verwenden.
PDNS Recursor wird als "Weiche" zwischen internen und externen Namen (z.B. Internet) genutzt.
PowerDNS Admin ist eine Weboberfläche zur Konfiguration des Authoritative Servers.
Getestet auf: AlmaLinux 8
=== Netzwerkeinstellungen ===
Als erstes eine feste IP vergeben:
vi /etc/sysconfig/network-scripts/ifcfg-ens18
ifcfg-ens18 durch den entsprechenden Netzwerkadapter ersetzen.
Hier ein Beispiel wie die Konfiguration aussehen könnte:
TYPE=Ethernet
PROXY_METHOD=none
BROWSER_ONLY=no
BOOTPROTO=none
DEFROUTE=yes
IPV4_FAILURE_FATAL=no
IPV6INIT=no
NAME=ens18
UUID=199dc4c1-d2d2-44c6-92b0-9f58b435fc2e
DEVICE=ens18
ONBOOT=yes
IPV6_DISABLED=yes
# Static IP
IPADDR=192.168.2.11
PREFIX=24
GATEWAY=192.168.2.1
DNS1=192.168.2.1
DNS2=1.1.1.1
Wichtig ist dabei, dass BOOTPROTO=dhcp auf BOOTPROTO=none geändert wird.
Eventuell noch den Hostnamen anpassen:
vi /etc/hostname
Dieser muss auch in der hosts-Datei angepasst werden:
vi /etc/hosts
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
192.168.2.11 dns-1 dns-1.my.domain
reboot
=== PowerDNS Authoritative Server und PDNS Recursor installieren ===
Abhängigkeiten installieren:
dnf install epel-release 
dnf install 'dnf-command(config-manager)' 
dnf config-manager --set-enabled powertools
dnf update
PowerDNS Recursor installieren: 
curl -o /etc/yum.repos.d/powerdns-rec-45.repo https://repo.powerdns.com/repo-files/centos-rec-45.repo
dnf install pdns-recursor
PowerDNS Authoritative Server installieren
curl -o /etc/yum.repos.d/powerdns-auth-45.repo https://repo.powerdns.com/repo-files/centos-auth-45.repo
dnf install pdns pdns-backend-mysql
=== Mariadb installieren ===
dnf install mariadb mariadb-server
Mariadb-Server einschalten und Autostart aktivieren:
systemctl enable --now mariadb
Falls noch kein root Passwort vergeben wurde sollte das jetzt nachgeholt werden:
passwd root
Datenbank absichern:
mysql_secure_installation
* Enter current password for root (enter for none): enter
* Set root password? [Y/n] y
* New password:
* Re-enter new password:
* Remove anonymous users? [Y/n] y
* Disallow root login remotely? [Y/n] y
* Remove test database and access to it? [Y/n] y
* Reload privilege tables now? [Y/n] y
In die Kommandozeile von Mariadb wechseln:
mysql -uroot -p
Befehle zum einrichten der Datenbank (Kann als ganzes kopiert und in der Konsole eingefügt werden [Letzte Zeile mit Enter abschließen]):
Datenbank und Benutzer erstellen (Passwort ändern):
CREATE DATABASE powerdns;
 GRANT ALL PRIVILEGES ON powerdns.* TO pdns@localhost identified by 'pdnspassword2018';
 FLUSH PRIVILEGES;
 USE powerdns;
Als nächstes die Tabellen erstellen:https://github.com/PowerDNS/pdns/blob/rel/auth-4.6.x/modules/gmysqlbackend/schema.mysql.sql
CREATE TABLE domains (
 id INT AUTO_INCREMENT,
 name VARCHAR(255) NOT NULL,
 master VARCHAR(128) DEFAULT NULL,
 last_check INT DEFAULT NULL,
 type VARCHAR(6) NOT NULL,
 notified_serial INT UNSIGNED DEFAULT NULL,
 account VARCHAR(40) CHARACTER SET 'utf8' DEFAULT NULL,
 PRIMARY KEY (id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE UNIQUE INDEX name_index ON domains(name);
CREATE TABLE records (
 id BIGINT AUTO_INCREMENT,
 domain_id INT DEFAULT NULL,
 name VARCHAR(255) DEFAULT NULL,
 type VARCHAR(10) DEFAULT NULL,
 content VARCHAR(64000) DEFAULT NULL,
 ttl INT DEFAULT NULL,
 prio INT DEFAULT NULL,
 disabled TINYINT(1) DEFAULT 0,
 ordername VARCHAR(255) BINARY DEFAULT NULL,
 auth TINYINT(1) DEFAULT 1,
 PRIMARY KEY (id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE INDEX nametype_index ON records(name,type);
CREATE INDEX domain_id ON records(domain_id);
CREATE INDEX ordername ON records (ordername);
CREATE TABLE supermasters (
 ip VARCHAR(64) NOT NULL,
 nameserver VARCHAR(255) NOT NULL,
 account VARCHAR(40) CHARACTER SET 'utf8' NOT NULL,
 PRIMARY KEY (ip, nameserver)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE TABLE comments (
 id INT AUTO_INCREMENT,
 domain_id INT NOT NULL,
 name VARCHAR(255) NOT NULL,
 type VARCHAR(10) NOT NULL,
 modified_at INT NOT NULL,
 account VARCHAR(40) CHARACTER SET 'utf8' DEFAULT NULL,
 comment TEXT CHARACTER SET 'utf8' NOT NULL,
 PRIMARY KEY (id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE INDEX comments_name_type_idx ON comments (name, type);
CREATE INDEX comments_order_idx ON comments (domain_id, modified_at);
CREATE TABLE domainmetadata (
 id INT AUTO_INCREMENT,
 domain_id INT NOT NULL,
 kind VARCHAR(32),
 content TEXT,
 PRIMARY KEY (id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE INDEX domainmetadata_idx ON domainmetadata (domain_id, kind);
CREATE TABLE cryptokeys (
 id INT AUTO_INCREMENT,
 domain_id INT NOT NULL,
 flags INT NOT NULL,
 active BOOL,
 published BOOL DEFAULT 1,
 content TEXT,
 PRIMARY KEY(id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE INDEX domainidindex ON cryptokeys(domain_id);
CREATE TABLE tsigkeys (
 id INT AUTO_INCREMENT,
 name VARCHAR(255),
 algorithm VARCHAR(50),
 secret VARCHAR(255),
 PRIMARY KEY (id)
) Engine=InnoDB CHARACTER SET 'latin1';
CREATE UNIQUE INDEX namealgoindex ON tsigkeys(name, algorithm);
Als letztes verlassen wir die Kommandozeile wieder:
EXIT;
=== PowerDNS Authoritative Server konfigurieren ===
Zuerst die Konfigurationsdatei öffnen:
vi /etc/pdns/pdns.conf
Damit PowerDNS-Admin auf den Server zugreifen kann muss die API aktiviert werden:
# api=no
api=yes
Einen API Key festelgen. Dieser wird später in zur Konfiguration von PowerDNS-Admin benötigt:
api-key=<Super sicherer Schlüssel>
Der Server soll im Hintergrund laufen:
# daemon=no
daemon=yes
Als nächstes den MySQL Backend konfigurieren:
# launch=bind
launch=gmysql
Danach ein paar Zeilen hinzufügen um die Verbindungsparameter anzugeben:
gmysql-host=localhost
gmysql-user=pdns
gmysql-password=pdnspassword2018
gmysql-dbname=powerdns
Da der Authoritative Server nur Anfragen vom Recursive bekommt, brauch dieser auch nur auf localhost laufen:
# local-address=0.0.0.0, ::
local-address=127.0.0.1
DNS Anfragen gehen zuerst an den Recursive und sollen erst in zweiter Instanz an den Authoritative weitergeleitet werden. 
Daher muss dieser auf einem andern Port laufen (z.B. 54):
# local-port=53
local-port=54
Damit PowerDNS-Admin später auf die API zugreifen kann muss die IP angepasst werden.
# webserver-address=127.0.0.1
webserver-address=172.17.0.1
# webserver-allow-from=127.0.0.1,::1
webserver-allow-from=172.0.0.0/8
Den PowerDNS Server einschalten und Autostart aktivieren:
systemctl enable --now pdns
Als nächstes sollte überprüft werden ob der Service läuft:
systemctl status pdns
Möglicherweise sind beim Starten Fehler aufgetreten...
Fehler Unable to open /etc/pdns/pdns.conf
Fehlende Berechtigung auf den Konfigurationsordner:
chown root:pdns -R /etc/pdns*
chmod 640 -R /etc/pdns*
Fehler Unable to bind UDP socket to '127.0.0.1:54': Permission denied
SELinux verhindert höchstwahrscheinlich, dass der DNS Server auf Port 54 läuft.
Standardmäßig erlaubt SELinux für DNS Server nur die Ports 53 & 853.
Mit folgenden Zeilen kann Port 54 hinzugefügt werden:
dnf install policycoreutils-python-utils
semanage port --add --type=dns_port_t --proto=udp 54
semanage port --add --type=dns_port_t --proto=tcp 54
Den Server neustarten
systemctl restart pdns
PowerDNS sollte nun ohne Fehler starten.
=== PowerDNS Recursor konfigurieren ===
Zunächst wieder die Konfigurationsdatei öffnen:
vi /etc/pdns-recursor/recursor.conf
Auch der Recursor soll im Hintergrund laufen:
# daemon=no
daemon=yes
Forward Zones z.B. für die eigene Domain und eine Reverse Zone für den IP-Bereich 192.168.0.0/24.
Alle Anfragen für my.domain (inkl. Subdomains) und die IPs 192.168.0.0 bis 192.168.255.255 werden an den Authoritative Server weitergeleitet.
forward-zones = my.domain.=127.0.0.1:54
forward-zones += 168.192.in-addr.arpa.=127.0.0.1:54
Alle Anfragen die nicht in den eben deklarierten Bereich fallen, sollen an einen anderen DNS Server weitergeleitet werden (z.B. den Gateway [192.168.2.1] oder den Google DNS [8.8.8.8]:
# forward-zones-recurse=
forward-zones-recurse = .=8.8.8.8
Der Recursive DNS soll von außen erreichbar sein:
# local-address=127.0.0.1
local-address=0.0.0.0
Den Recursive Server einschalten und Autostart aktivieren:
systemctl enable --now pdns-recursor
Zu guter Letzt muss noch der DNS-Port in der Firewall geöffnet werden:
firewall-cmd --permanent --add-service=dns
firewall-cmd --reload
=== PowerDNS-Admin installieren (Als Docker Container) ===
Zuerst die Docker "Community Edition" installieren:
dnf config-manager --add-repo=https://download.docker.com/linux/centos/docker-ce.repo
dnf install docker-ce docker-ce-cli containerd.io
Docker einschalten und Autostart aktivieren:
systemctl enable --now docker
Den Container mit PowerDNS-Admin herunterladen und starten:
docker run -d --env=SECRET_KEY=<Sicheres Passwort> --volume=pda-data:/data -p 80:80 --restart=always ngoduykhanh/powerdns-admin:latest
Damit der pdns-Service erst nach dem Docker startet und den Webserver auf 172.17.0.1:8081 öffnen kann
vi /usr/lib/systemd/system/pdns.service
Am Ende der Zeile "After" den docker.service anfügen. Damit startet PowerDNS erst nach dem Docker.
After=network-online.target mysqld.service postgresql.service slapd.service mariadb.service docker.service
Abschließend den systemd-Daemon neu laden
systemctl daemon-reload
Der Authoritative Server muss noch einmal neu gestartet werden:
systemctl restart pdns
Mit ss -tulnp | grep LISTEN kann kontrolliert werden ob alles benötigten Ports geöffnet sind.
tcp LISTEN 0 128 0.0.0.0:80 0.0.0.0:* users:(("docker-proxy",pid=7073,fd=4))
tcp LISTEN 0 10 172.17.0.1:8081 0.0.0.0:* users:(("pdns_server",pid=7195,fd=9))
tcp LISTEN 0 128 0.0.0.0:53 0.0.0.0:* users:(("pdns_recursor",pid=3929,fd=5))
tcp LISTEN 0 128 127.0.0.1:54 0.0.0.0:* users:(("pdns_server",pid=7195,fd=8))
tcp LISTEN 0 80 *:3306 *:* users:(("mysqld",pid=884,fd=21))
tcp LISTEN 0 128 [::]:80 [::]:* users:(("docker-proxy",pid=7081,fd=4))
*Port 80: PowerDNS-Admin Weboberfläche
*Port 8081: PowerDNS Authoritative Server API
*Port 53: PowerDNS Recursor (DNS Server für alle Anfragen)
*Port 54: PowerDNS Authoritative
Damit PowerDNS-Admin von außen erreichbar ist muss noch der Port in der Firewall freigegeben werden.
firewall-cmd --permanent --zone=public --add-service=http
firewall-cmd --reload
PowerDNS-Admin wäre nach diesem Beispiel jetzt unter http://192.168.2.11 zu erreichen!
Als erstes erstellen wir einen neuen Benutzer
Direkt im Anschluss kann man sich mit dem Benutzer anmelden (Der erste Benutzer hat automatisch Administrator Rechte)
Danach muss die PDNS Verbindung konfiguriert werden
* PDNS API URL: http://172.17.0.1:8081/
* PDNS API KEY: API Key aus der pdns.conf eingeben
* PDNS VERSION: 4.5.2 (Die korrekte Version kann mit dem Befehl pdns_server --version ermittelt werden.
Unter dem Menüpunkt PDNS sollten jetzt einige Einträge zu sehen sein.
Unter Settings->Authentication "Allow user to sign up" deaktivieren damit sich nicht jeder einen neuen Account erstellen kann.
Glückwunsch, dein DNS Server läuft nun!
Forward Zone für Domain->IP erstellen:
Datei:PowerDNS-Admin - Neue Domain erstellen.png
Datei:PowerDNS-Admin Homepage.png
Datei:PowerDNS-Admin - Domaineinträge bearbeiten A-Record.png
Reverse Zone für IP->Domain erstellen:
Datei:PowerDNS-Admin - Reverse Zone erstellen.png
Datei:PowerDNS-Admin Homepage - Reverse Lookup.png
Datei:PowerDNS-Admin - Reverse Zone bearbeiten - PTR erstellen.png
==Quellen==
https://www.howtoforge.com/how-to-install-powerdns-and-poweradmin-on-centos-7/
https://doc.powerdns.com/authoritative/installation.html
https://doc.powerdns.com/authoritative/backends/generic-mysql.html
https://doc.powerdns.com/authoritative/guides/recursion.html
https://github.com/PowerDNS-Admin/PowerDNS-Admin
===Einzelnachweise===
== Kommentare ==
<comments nocache="true" />
Kategorie:AlmaLinux
Kategorie:Network