Mich hat die zunehmend kommerzielle Natur von DynDNS in letzter Zeit mehr und mehr angenervt. Außerdem ging die (gefühlte) Zuverlässigkeit immer weiter zurück. Also musste eine neue Lösung her, idealerweise auch eine, bei der ich Hosts meiner eigenen Domain dynamisch vergeben kann, und das ohne externe Dienstleister (einfach der Coolness wegen).
Mein schnell zusammengehacktes System hier besteht jetzt aus zwei Elementen: Einerseits muss der dynamische Host dem Server irgendwie mitteilen, wie seine IP lautet, andererseits muss der Server die neue IP in die Welt hinausposaunen.
Für den ersten Teil habe ich genutzt, was da war: Zu Hause steht ein Linksys mit OpenWRT, auf dem Server läuft ohnehin ein Webserver, der auch CGI spricht (Natürlich würde sich hier auch jeder andere Service eignen, bei dem eine Verbindung aufgebaut und irgend eine Art von Authentifizierung durchgeführt wird. Meine Variante hat aber den netten Vorteil, dass hier auf Serverseite ein Skript angestoßen wird, was die IP des dynamischen Hosts einfach in eine Datei schreiben kann. Andere benutzen an der Stelle SSH oder POP, aber dann muss man die IP-Adresse hinterher umständlich aus irgendwelchen Logfiles popeln.). Auf dem Linksys läuft der folgende Cronjob:
/usr/bin/wget -O /dev/null "http://www.example.com/cgi-bin/ipupdate?foobar" >/dev/null 2>/dev/null
Der String “foobar” in der URL erfüllt dabei die Funktion eines Passworts, um ein Mindestmaß an Authentifizierung sicherzustellen. Man kann die Sache an dieser Stelle beliebig komplex machen, aber für mich reicht es. Das ipupdate-Skript auf Serverseite sieht folgendermaßen aus:
#!/bin/sh
echo "Content-type: text/html\n"
if [ "$QUERY_STRING" = "foobar" ] ; then
echo "$REMOTE_ADDR" > /tmp/ip.txt
fi
Es tut nichts anderes als zu prüfen, ob das Passwort stimmt und wenn ja, schreibt es die IP-Adresse des Clients in eine Datei. Diese IP-Adresse muss nun natürlich noch an einen DNS-Server verfüttert werden. Wer keinen eigenen DNS-Server hat, sondern den seines Providers verwendet (mache ich normalerweise auch so), kann sich nun ein Skript schreiben, was im Administrations-Interface des Providers die IP-Adresse des Hosts ändert. Das ist sicher möglich, war mir aber einerseits zu kompliziert, andererseits haben die Einträge beim DNS-Server meines Providers eine lange Lebensdauer von 86400 Sekunden, die ich nicht anpassen kann. Übliche Cachelebensdauern sind zwar meist kürzer, aber ich habe dennoch keine Kontrolle darüber, wie lange die alte IP von anderen Servern ggf. noch verwendet wird, ohne mal nach der neuen zu fragen.
Also habe ich einfach selbst einen primitiven DNS-Server mit minimalistischer Konfiguration eingerichtet. BIND ist natürlich totaler Overkill an dieser Stelle, also habe ich mich für MaraDNS entschieden. Die MaraDNS-Konfiguration ist nicht schwierig, ich habe lediglich folgendes in meiner Konfigurationsdatei stehen:
bind_address = "127.0.0.1 1.2.3.4"
chroot_dir = "/etc/maradns"
csv2 = {}
csv2["dynamic.example.com."] = "db.dynamic.example.com"
Hierbei ist 1.2.3.4 die externe IP-Adresse des Servers und dynamic.example.com der Host, unter dem der Rechner mit der dynamischen IP später erreichbar sein soll.
Was nun noch fehlt, ist das Zonefile. MaraDNS liest seine Zonefiles leider nur neu, wenn man es beendet und neu startet (das ist in meinem Fall kein großes Problem, weil meine dynamische IP sich nur selten ändert – im Idealfall einmal am Tag – möchte man viele oder schnell wechselnde IPs verteilen, muss man sich hier natürlich etwas anderes einfallen lassen). Ich habe an dieser Stelle einen Cronjob als root eingerichtet, der minütlich folgendes Skript aufruft:
#!/bin/sh
[ -e /tmp/ip.txt -a -e /etc/maradns/db.dynamic.example.com ] || exit 1
if [ `cat /tmp/ip.txt` != `cut -d " " -f 4 /etc/maradns/db.dynamic.example.com` ] ; then
echo "dynamic.example.com. +60 A `cat /tmp/ip.txt` ~" > /etc/maradns/db.dynamic.example.com
/etc/init.d/maradns restart >/dev/null
fi
Es vergleicht den (von ihm selbst in einem früheren Lauf angelegten) alten Eintrag im Zonefile (das deshalb nur eine Zeile mit eben diesem Eintrag haben sollte, die am Schluss einfach wieder überschrieben wird) mit der letzten vom dynamischen Host gemeldeten IP-Adresse. Falls sich die IP-Adresse geändert haben sollte, wird das Zonefile aktualisiert und der DNS-Server neu gestartet.
Man muss nun natürlich noch dem DNS-Server seines Providers mitteilen, dass er die Anfragen für die Subdomain dynamic.example.com an den eigenen Nameserver delegiert. Ob und wie das geht, ist natürlich von Provider zu Provider unterschiedlich – ich konnte es bequem im Webinterface klicken.