DynDNS

Aus Leupers.net-Wiki
Wechseln zu: Navigation, Suche

DynDNS-Dienste

Aktuell verwende ich den folgenden DynDNS-Dienst (Stand: 2014-05-01)

Sonstige:

Linux Clients

Die meisten werden zuhause einen Router haben, der auch DynDNS unterstützt. Das kann zwar mein alter Speedport-DSL-Router von der Telekom auch schon, aber leider nur für dyndns.org und nicht für andere DynDNS-Dienste. Daher habe ich DynDNS auf dem Router jetzt deaktiviert und lasse die IP-Adresse beim DynDNS-Dienst jetzt von einem Linux-Rechner aus aktualisieren.

ddclient

Tutorials

FreeDNS & ddclient

ACHTUNG:
Laut FreeDNS-Seite funktioniert ddclient erst ab Version 3.8.1 einwandfrei mit FreeDNS!
(siehe Dynamic DNS clients; suche nach "ddclient")

Da auf dem Rechner, wo der ddclient (bisher für dyndns.org) lief, leider nur die ältere ddclient-Version 3.8.0 installiert ist, verwende ich die einfache IP-Update-Lösung über einen cronjob; siehe unten.

Web-basiert per cronjob

Wenn man den kostenlosen Dienst "FreeDNS" verwendet, kann man die dynamische IP-Adresse auch ganz einfach per Webaufruf aktuell halten.

Um dafür einen cronjob zu erstellen, kann man einfach als normaler User (das kann/muss/soll NICHT root sein!) folgendes aufrufen:

$ crontab -e

Es öffnet sich eine Datei im Editor. Dort fügt man einfach am Ende folgendes hinzu:

*/5   *   *   *   *     /usr/bin/wget -q -o /dev/null -O - https://freedns.afraid.org/dynamic/update.php?<EIGENE-ID> /dev/null 2>&1

Die dafür notwendige URL mit der eindeutigen ID für den entsprechenden DynDNS-Eintrag findet man, wenn man in FreeDNS eingeloggt ist, auf der Seite Dynamic DNS unten unter dem Link "Direct URL example".
Im Firefox kann man die URL einfach über Rechts-Click und "Link-Adresse kopieren" in die Zwischenablage kopieren und so übernehmen.

Hinweis: Die eigene ID sollte nicht in falsche Hände geraten, da damit sonst jeder die dynamische Domain auf seine eigene IP umleiten könnte.
Im cronjob-Aufruf habe ich daher noch das "http" durch "https" ersetzt, damit die Übertragung verschlüsselt abläuft und somit geschützt ist.

Eigentlich würde ich ja einen intelligenteren Client - wie ddclient - bevorzugen, da man den recht leicht so konfigurieren könnte, dass er nur noch Updates schickt, wenn sich die IP-Adresse auch wirklich geändert hat, aber da bei mir noch eine ältere ddclient-Version installiert ist, die mit FreeDNS noch nicht so gut zurecht kommt (s.o.), muss es jetzt halt erst mal per cronjob laufen. Geht ja auch... ;-)

More Clients

Eigene, externe IP-Adresse ermitteln

Einfach die folgende Seite aufrufen:

http://checkip.dyndns.com/

Das Ergebnis ist eine minimalistische Webseite, wie die folgende, wobei da statt "a.b.c.d" natürlich IP-Adresse steht:

<html><head><title>Current IP Check</title></head><body>Current IP Address: a.b.c.d</body></html>


Freien Dyn.com Account verlängern

HINWEIS (2014-05-01):
Am 7. Mai 2014 stellt DynDNS leider den kostenlosen Dienst ganz ein.
Ich bin jetzt zur Alternative FreeDNS gewechselt; siehe oben.
Das nachfolgende Skript wird daher nicht mehr benötigt, aber vielleicht kann man es ja für ähnliche Probleme später nochmal in ähnlicher Form brauchen!?

Problem

Seit Mai 2013 hat Dyn leider die Bedingungen für die kostenlose Nutzung verschärft. Man muss seither nicht nur mindestens einmal alle 30 Tage die dynamische IP-Adresse aktualisieren (wie bisher), sondern sich außerdem alle 30 Tage einmal auf der Webseite einloggen. - Falls man dies nicht tut, wird der Account wohl deaktiviert.

Ich habe irgendwie den Eindruck, dass sie nicht-zahlende Nutzer loswerden wollen. ;-)

Lösung

Eine kurze Recherche hat mich auf die folgende sehr hilfreiche Seite geführt, die zeigt, wie man den nun regelmäßig obligatorischen Web-Login automatisieren kann:

   DynDNS wird unbenutzbar

Ich habe die Basis des obigem Skripts verwendet und ausgebaut. Man kann es manuell auf der Shell ausführen, aber es ist eigentlich dazu gedacht per cron-Job automatisiert ausgeführt zu werden (s.u.).

Features:

  • Login, Check auf erfolgreichen Login und Logout auf dyn.com.
  • Unterstützung von mehreren Dyn-Accounts. (Variablen USRS und PWDS ändern/ergänzen.)
  • Ergebnisse werden am Ende TLS-verschlüsselt über SMTP gemailt, wobei Logfiles als Attachment angehängt werden.
    • Der verschlüsslte Email-Versand wurde erfolgreich getestet mit 1&1 und GMX.
    • Dazu wird intern das Tool "sendEmail" verwendet. Installation unter (K)Ubuntu:
# sudo apt-get install sendEmail libio-socket-ssl-perl libnet-ssleay-perl perl

Weitere Details: Bash - Emails per Skript über SMTP versenden

Download des nachfolgenden Skripts:

#!/bin/bash
################################################################################
#
# NAME
#    dyndns-web-login.sh
#
# PURPOSE
#    Login into Dyn website (and log out again immediately)
#    just to refresh the account, because in May 2013 they introduced
#    the need to log in to your account on their webpage once a month
#    for users of their free accounts. Otherwise the account would expire.
#
# HISTORY
#    2013-05-20 Inital version.
#
################################################################################

# List of user accounts and corresponding passwords.
USRS=("User1"     "User2")
PWDS=("Password1" "Password2")

# Must be adapted as needed.
MAILSMTP="smtp.1und1.de:587"
MAILUSER="MyUser"
MAILPASS="MyPassword"
MAILFROM="Sender@domain.de"
MAILTO="me@mydomain.de"
TLS=1

# May be set to "1" (one) to enable more verbose output for debugging.
VERBOSE=1

# Normally no need to change.
URL="https://account.dyn.com/entrance/"
LOG="/tmp/dyndns-$$.log"
LOGWGET="/tmp/dyndns-$$_wget.log"
LOGSENDEMAIL="/tmp/dyndns-$$_sendemail.log"
COOKIES="/tmp/dyndns-$$_cookies.txt"
LOGINPREFIX="/tmp/dyndns-$$_login_"
ACCOUNTPREFIX="/tmp/dyndns-$$_account_"
LOGOUTPREFIX="/tmp/dyndns-$$_logout_"
LOGINPOSTFIX=".html"
ACCOUNTPOSTFIX=".html"
LOGOUTPOSTFIX=".html"
# Must be a full list of temporary files to send/delete!
MAILFILES="$LOGWGET $COOKIES"
for ((i=0; i < ${#USRS[*]}; i++)) ; do
   MAILFILES="$MAILFILES ${LOGINPREFIX}${USRS[$i]}${LOGINPOSTFIX}"
   MAILFILES="$MAILFILES ${ACCOUNTPREFIX}${USRS[$i]}${ACCOUNTPOSTFIX}"
   MAILFILES="$MAILFILES ${LOGOUTPREFIX}${USRS[$i]}${LOGOUTPOSTFIX}"
done
TMPFILES="$MAILFILES $LOG $LOGSENDEMAIL"

# DO NOT CHANGE!
SUCCESS=1

#-------------------------------------------------------------------------------

function clean()
{
   echo "Cleaning up temp files..." | tee -a $LOG

   for file in $TMPFILES ; do
      #echo "- $file"                | tee -a $LOG
      rm -f $file
   done
   
   echo                             | tee -a $LOG
}

#-------------------------------------------------------------------------------

function emailResult()
{
   MAILPARAMS=
   if [ $VERBOSE -eq 1 ] ; then
      MAILPARAMS="-v"
   fi
   if [ $TLS -eq 1 ] ; then
      MAILPARAMS="$MAILPARAMS -o tls=yes"
   fi
   if [ $SUCCESS -eq 1 ] ; then
      SUBJECT="[DynDNS] Account-Refresh-Login successful."
   else
      SUBJECT="[DynDNS] ERROR: Account-Refresh-Login failed!"
   fi

   MAILPARAMS="$MAILPARAMS -s $MAILSMTP -xu $MAILUSER -xp $MAILPASS"
   MAILPARAMS="$MAILPARAMS -o message-charset=utf-8 -f $MAILFROM -t $MAILTO -u $SUBJECT"
   MAILPARAMS="$MAILPARAMS -o message-content-type=text -o message-file=$LOG"
   
   # if not successful, add logfiles for debugging
   #if [ $SUCCESS -eq 0 ] ; then
      for file in $MAILFILES ; do
         if [ -f $file ] ; then
            MAILPARAMS="$MAILPARAMS -a $file"
         fi
      done
   #fi

   echo -n "Sending email to '$MAILFROM'..."
   sendEmail $MAILPARAMS > $LOGSENDEMAIL 2>&1
   RC=$?
   if [ $RC -eq 0 ] ; then
      echo "  -->  OK"
   else
      echo "  -->  ERROR: sendEmail exit code = $RC"
      echo "- Command was: sendEmail $MAILPARAMS > $LOGSENDEMAIL 2>&1"
      echo "----- sendEmail logfile -----"
      cat $LOGSENDEMAIL
      echo "----- END -----"
   fi
}

#-------------------------------------------------------------------------------

function abort()
{
   errorMsg="$*"
   
   echo "  -->  ERROR: $errorMsg :-(" | tee -a $LOG
   echo                               | tee -a $LOG
   echo "Aborting..."                 | tee -a $LOG
   echo                               | tee -a $LOG

   SUCCESS=0
   emailResult
   
   clean
   
   exit 1
}

#-------------------------------------------------------------------------------

function wgetErrorText()
{
   errorCode=$1
   
   if [ $errorCode -eq 0 ] ; then
      echo "No problems occurred. [$errorCode]"
   elif [ $errorCode -eq 1 ] ; then
      echo "Generic error code. [$errorCode]"
   elif [ $errorCode -eq 2 ] ; then
      echo "Parse error---for instance, when parsing command-line options, the .wgetrc or .netrc... [$errorCode]"
   elif [ $errorCode -eq 3 ] ; then
      echo "File I/O error. [$errorCode]"
   elif [ $errorCode -eq 4 ] ; then
      echo "Network failure."
   elif [ $errorCode -eq 5 ] ; then
      echo "SSL verification failure. [$errorCode]"
   elif [ $errorCode -eq 6 ] ; then
      echo "Username/password authentication failure. [$errorCode]"
   elif [ $errorCode -eq 7 ] ; then
      echo "Protocol errors. [$errorCode]"
   elif [ $errorCode -eq 8 ] ; then
      echo "Server issued an error response. [$errorCode]"
   else
      echo "Unknown error. [$errorCode]"
   fi 
}

#-------------------------------------------------------------------------------

function checkResult()
{
   USR=$1

   echo -n "- Checking for login name...         " | tee -a $LOG
   grep --color=auto "<b>$USR</b>" ${ACCOUNTPREFIX}${USR}${ACCOUNTPOSTFIX} > /dev/null
   if [ $? -eq 0 ] ; then
      echo "  -->  OK, successfully logged in!"    | tee -a $LOG
   else
      abort "Login seems to be failed!"
   fi
}

#-------------------------------------------------------------------------------

function connect()
{
   USR=$1
   PWD=$2
   
   echo "Connecting as '$USR' to '$URL':"          | tee -a $LOG

   echo -n "- Fetching login in page...          " | tee -a $LOG
   wget -O ${LOGINPREFIX}${USR}${LOGINPOSTFIX} --save-cookies $COOKIES ${URL} >> $LOGWGET 2>&1
   RC=$?
   if [ $RC -eq 0 ] ; then
      echo "  -->  OK"                             | tee -a $LOG
   else
      abort "$(wgetErrorText $RC)"
   fi

   FOUND=0
   MULTI=''
   while read line; do
      if [ `egrep -c "<form id='login" <<< $line`   -gt 0 ] ; then FOUND=1; fi
      if [ `egrep -c "</form>"         <<< ${line}` -gt 0 ] ; then FOUND=0; fi
      if [ `egrep -c "multiform"       <<< ${line}` -gt 0 -a $FOUND -eq 1 ]; then
         MULTI=`sed -e "s/.*value='\([[:alnum:]]*\)'.*/\1/" <<< ${line}`
      fi
   done < ${LOGINPREFIX}${USR}${LOGINPOSTFIX}

   echo -n "- Logging in...                      "  | tee -a $LOG
   wget -O ${ACCOUNTPREFIX}${USR}${ACCOUNTPOSTFIX} --load-cookies $COOKIES \
        --post-data="username=${USR}&password=${PWD}&multiform=${MULTI}" \
        ${URL} >> $LOGWGET 2>&1 
   RC=$?
   if [ $RC -eq 0 ] ; then
      echo "  -->  OK" | tee -a $LOG
   else
      abort "$(wgetErrorText $RC)"
   fi
   
   checkResult ${USR}

   echo -n "- Sleeping...                        " | tee -a $LOG
   sleep 2
   echo "  -->  OK"                                | tee -a $LOG
   
   echo -n "- Logging out...                     " | tee -a $LOG
   wget -O ${LOGOUTPREFIX}${USR}${LOGOUTPOSTFIX} --load-cookies $COOKIES ${URL}?__logout=1 >> $LOGWGET 2>&1
   RC=$?
   if [ $RC -eq 0 ] ; then
      echo "  -->  OK"                             | tee -a $LOG
   else
      abort "$(wgetErrorText $RC)"
   fi
   
   echo                                            | tee -a $LOG
}

################################################################################
### MAIN
################################################################################

LANG=C

for ((i=0; i < ${#USRS[*]}; i++)) ; do
   connect ${USRS[$i]} ${PWDS[$i]}
done

emailResult

clean

exit 0;

Dann einfach das Skript per cron-Job auf einem Linux-Rechner regelmäßig - z. B. einmal pro Woche - ausführen lassen. Dazu führt man als normaler User das folgende Kommando aus

# crontab -e

und trägt im sich dann öffnenden Editor die folgende Zeile ein:

0  18  *  *  5  /home/stefan/tools/dyndns-web-login.sh > /dev/null 2>&1

Erklärung:
Jeden Freitagabend um 18 Uhr ausführen. Dabei werden alle Ausgaben ins Nirvana geschickt, damit crontab keine Email über einen - bei mir nicht vorhandenen - lokalen Mailserver verschickt. Statt dessen wird im Skript per SMTP eine Mail mit allen Logfiles etc. verschickt.

Danach sollte es - hoffentlich - keine Probleme bei der weiteren Nutzung von Dyn geben. :-)

Links