mirror of
https://github.com/freedombox/FreedomBox.git
synced 2026-01-21 07:55:00 +00:00
added a module and a action script to manage ez-ipupdate tool, which provides dynamic IP updates to a gnudip dynamic DNS Server
This commit is contained in:
parent
4010b81ecc
commit
56208e007d
261
actions/dynamicDNS
Executable file
261
actions/dynamicDNS
Executable file
@ -0,0 +1,261 @@
|
||||
#!/bin/bash
|
||||
#Todo: IPv6
|
||||
#Todo: Other service types than gnudip (generic update URL)
|
||||
#Todo: GET WAN IP from Router via UPnP if supported
|
||||
|
||||
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
|
||||
|
||||
#static values
|
||||
EMPTYSTRING="none"
|
||||
NOIP="0.0.0.0"
|
||||
#how often do we poll for IP changes if we are behind a NAT?
|
||||
UPDATEMINUTES=5
|
||||
#if we do not have a IP check URL, how often should we do a "blind" update
|
||||
UPDATEMINUTESUNKNOWN=3600
|
||||
TOOLNAME=ez-ipupdate
|
||||
UPDATE_TOOL=$(which ${TOOLNAME})
|
||||
|
||||
#Dirs and filenames
|
||||
CFGDIR="/etc/${TOOLNAME}/"
|
||||
CFG="${CFGDIR}${TOOLNAME}.conf"
|
||||
CFG_disabled="${CFGDIR}${TOOLNAME}.inactive"
|
||||
IPFILE="${CFGDIR}${TOOLNAME}.currentIP"
|
||||
STATUSFILE="${CFGDIR}${TOOLNAME}.status"
|
||||
LASTUPDATE="${CFGDIR}/last-update"
|
||||
HELPERCFG="${CFGDIR}${TOOLNAME}-plinth.cfg"
|
||||
CRONJOB="/etc/cron.d/${TOOLNAME}"
|
||||
|
||||
doReadCFG()
|
||||
{
|
||||
host=""
|
||||
server=""
|
||||
user=""
|
||||
pass=""
|
||||
IPURL=""
|
||||
FILE=""
|
||||
[ -f $CFG_disabled ] && FILE=$CFG_disabled
|
||||
[ -f $CFG ] && FILE=$CFG
|
||||
|
||||
if [ ! -z $FILE ];then
|
||||
host=`cat $FILE 2> /dev/null |grep host |cut -d = -f 2`
|
||||
server=`cat $FILE 2> /dev/null |grep server |cut -d = -f 2`
|
||||
user=`cat $FILE 2> /dev/null |grep user |cut -d = -f 2 |cut -d : -f 1`
|
||||
pass=`cat $FILE 2> /dev/null |grep user |cut -d = -f 2 |cut -d : -f 2`
|
||||
fi
|
||||
|
||||
if [ ! -z $HELPERCFG ];then
|
||||
IPURL=`cat $HELPERCFG 2> /dev/null |grep URL |awk '{print $2}'`
|
||||
fi
|
||||
}
|
||||
|
||||
doGetOpt()
|
||||
{
|
||||
while getopts ":s:d:u:p:I:" opt; do
|
||||
case $opt in
|
||||
s)
|
||||
server=$OPTARG
|
||||
;;
|
||||
d)
|
||||
host=$OPTARG
|
||||
;;
|
||||
u)
|
||||
user=$OPTARG
|
||||
;;
|
||||
p)
|
||||
pass=$OPTARG
|
||||
;;
|
||||
I)
|
||||
if [ "$OPTARG" != "$EMPTYSTRING" ];then
|
||||
IPURL=$OPTARG
|
||||
else
|
||||
IPURL=""
|
||||
fi
|
||||
;;
|
||||
\?)
|
||||
echo "Invalid option: -$OPTARG" >&2
|
||||
exit 1
|
||||
;;
|
||||
:)
|
||||
echo "Option -$OPTARG requires an argument." >&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
done
|
||||
}
|
||||
|
||||
doWriteCFG()
|
||||
{
|
||||
#always write to the inactive config - needs to be enabled vi "start" command later
|
||||
FILE=$CFG_disabled
|
||||
|
||||
#reset the last update time
|
||||
echo 0 > $LASTUPDATE
|
||||
|
||||
#reset the last updated IP
|
||||
echo "0.0.0.0" > $IPFILE
|
||||
|
||||
#reset last update
|
||||
rm $STATUSFILE
|
||||
|
||||
#find the interface (always the default gateway interface)
|
||||
DEFAULT=`ip route |grep default |awk '{print $5}'`
|
||||
|
||||
#store the given options in ez-ipupdate compatible config file
|
||||
echo "host=$host" > $FILE
|
||||
echo "server=$server" >> $FILE
|
||||
echo "user=${user}:${pass}" >> $FILE
|
||||
echo "service-type=gnudip" >> $FILE
|
||||
echo "retrys=5" >> $FILE
|
||||
echo "execute=$0 success" >> $FILE
|
||||
echo "wildcard" >> $FILE
|
||||
|
||||
#check if we are behind a NAT Router
|
||||
echo "IPURL $IPURL" > $HELPERCFG
|
||||
if [ -z $IPURL ];then
|
||||
echo "NAT unknown" >> $HELPERCFG
|
||||
else
|
||||
doGetWANIP
|
||||
ISGLOBAL=`ip addr ls $DEFAULT | grep $WANIP`
|
||||
if [ -z $ISGLOBAL ];then
|
||||
#we are behind NAT
|
||||
echo "NAT yes" >> $HELPERCFG
|
||||
else
|
||||
#we are directly connected
|
||||
echo "NAT no" >> $HELPERCFG
|
||||
#if this file is added ez-ipupdate will take ip form this interface
|
||||
echo "interface=$DEFAULT" >> $FILE
|
||||
#if this line is added to config file, ez-ipupdate will be launched on startup via init.d
|
||||
echo "daemon" >> $FILE
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
||||
doGetWANIP()
|
||||
{
|
||||
if [ $IPURL ];then
|
||||
OUTFILE=`mktemp`
|
||||
wget -4 -o /dev/null -O $OUTFILE $IPURL
|
||||
WANIP=`cat $OUTFILE`
|
||||
rm $OUTFILE
|
||||
else
|
||||
#no WAN IP found because of missing check URL
|
||||
WANIP=${NOIP}
|
||||
fi
|
||||
echo $WANIP > $IPFILE
|
||||
}
|
||||
|
||||
cmd=$1
|
||||
shift
|
||||
case $cmd in
|
||||
configure)
|
||||
doGetOpt $@
|
||||
doWriteCFG
|
||||
;;
|
||||
start)
|
||||
if [ "$(cat $HELPERCFG |grep ^NAT | awk '{print $2}')" = "no" ];then
|
||||
mv $CFG_disabled $CFG
|
||||
/etc/init.d/${TOOLNAME} start
|
||||
else
|
||||
echo "*/${UPDATEMINUTES} * * * * root $0 update" > $CRONJOB
|
||||
$0 update
|
||||
fi
|
||||
;;
|
||||
get-nat)
|
||||
NAT=`cat $HELPERCFG 2> /dev/null |grep ^NAT | awk '{print $2}'`
|
||||
[ -z $NAT ] && NAT="unknown"
|
||||
echo $NAT
|
||||
;;
|
||||
update)
|
||||
doReadCFG
|
||||
OLDIP=`cat $IPFILE`
|
||||
doGetWANIP
|
||||
[ -f $CFG_disabled ] && FILE=$CFG_disabled
|
||||
[ -f $CFG ] && FILE=$CFG
|
||||
RESULT=0
|
||||
#if we know our WAN IP, only update if IP changes
|
||||
if [ "$OLDIP" != "$WANIP" -a "${WANIP}" != ${NOIP} ];then
|
||||
${UPDATE_TOOL} -c $FILE
|
||||
RESULT=$?
|
||||
cat /proc/uptime |awk '{print $1}' > $LASTUPDATE
|
||||
fi
|
||||
#if we don't know our WAN IP do a blind update once a hour
|
||||
if [ "${WANIP}" = ${NOIP} ];then
|
||||
UPTIME=`cat /proc/uptime`
|
||||
LAST=`cat $LASTUPDATE`
|
||||
DIFF=`expr $UPTIME - $LAST`
|
||||
if [ $DIFF -gt $UPDATEMINUTESUNKNOWN ];then
|
||||
${UPDATE_TOOL} -c $FILE
|
||||
RESULT=$?
|
||||
cat /proc/uptime |awk '{print $1}' > $LASTUPDATE
|
||||
fi
|
||||
fi
|
||||
if [ $RESULT -eq 0 ];then
|
||||
$0 success
|
||||
else
|
||||
$0 failed
|
||||
fi
|
||||
;;
|
||||
stop)
|
||||
rm $CRONJOB 2> /dev/null
|
||||
/etc/init.d/${TOOLNAME} stop
|
||||
mv $CFG $CFG_disabled
|
||||
;;
|
||||
success)
|
||||
DATE=`date`
|
||||
echo "last update done ($DATE)" > $STATUSFILE
|
||||
;;
|
||||
failed)
|
||||
DATE=`date`
|
||||
echo "last update failed ($DATE)" > $STATUSFILE
|
||||
;;
|
||||
get-last-success)
|
||||
if [ -f $STATUSFILE ];then
|
||||
cat $STATUSFILE
|
||||
else
|
||||
echo "no update recorded since last config change"
|
||||
fi
|
||||
;;
|
||||
get-installed)
|
||||
if [ ! -z ${UPDATE_TOOL} ];then
|
||||
echo "installed"
|
||||
fi
|
||||
;;
|
||||
status)
|
||||
doReadCFG
|
||||
PROC=`pgrep ${TOOLNAME}`
|
||||
if [ -f $CRONJOB ];then
|
||||
echo enabled
|
||||
elif [ ! -z $PROC ];then
|
||||
echo enabled
|
||||
else
|
||||
echo disabled
|
||||
fi
|
||||
echo $server
|
||||
echo $host
|
||||
echo $user
|
||||
echo $pass
|
||||
echo $IPURL
|
||||
;;
|
||||
get-timer)
|
||||
echo $UPDATEMINUTES
|
||||
;;
|
||||
clean)
|
||||
rm ${CFGDIR}/*
|
||||
;;
|
||||
*)
|
||||
echo "usage: get-installed|status|configure <options>|start|stop|update|get-nat|clean|success|failed"
|
||||
echo ""
|
||||
echo "options are:"
|
||||
echo "-s <server> Gnudip Server address"
|
||||
echo "-d <domain> Domain to be updated"
|
||||
echo "-u <user> Account username"
|
||||
echo "-p <password> Account Password"
|
||||
echo "-I <IP check URL> A URL which returns the IP of the client who is requesting"
|
||||
echo ""
|
||||
echo "update do a one time update"
|
||||
echo "clean delete configuration"
|
||||
echo "success store update success"
|
||||
echo "failed store update failure"
|
||||
;;
|
||||
esac
|
||||
exit 0
|
||||
1
data/etc/plinth/modules-enabled/dynamicDNS
Normal file
1
data/etc/plinth/modules-enabled/dynamicDNS
Normal file
@ -0,0 +1 @@
|
||||
plinth.modules.dynamicDNS
|
||||
27
plinth/modules/dynamicDNS/__init__.py
Normal file
27
plinth/modules/dynamicDNS/__init__.py
Normal file
@ -0,0 +1,27 @@
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
|
||||
"""
|
||||
Plinth module to configure XMPP server
|
||||
"""
|
||||
|
||||
from . import dynamicDNS
|
||||
from .dynamicDNS import init
|
||||
|
||||
__all__ = ['xmpp2', 'init']
|
||||
|
||||
depends = ['plinth.modules.apps']
|
||||
245
plinth/modules/dynamicDNS/dynamicDNS.py
Normal file
245
plinth/modules/dynamicDNS/dynamicDNS.py
Normal file
@ -0,0 +1,245 @@
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
|
||||
from django import forms
|
||||
from django.contrib import messages
|
||||
from django.contrib.auth.decorators import login_required
|
||||
from django.core import validators
|
||||
from django.core.urlresolvers import reverse_lazy
|
||||
from django.template.response import TemplateResponse
|
||||
from gettext import gettext as _
|
||||
import logging
|
||||
|
||||
from plinth import actions
|
||||
from plinth import cfg
|
||||
|
||||
LOGGER = logging.getLogger(__name__)
|
||||
|
||||
subsubmenu = [{'url': reverse_lazy('dynamicDNS:index'),
|
||||
'text': _('About')},
|
||||
{'url': reverse_lazy('dynamicDNS:configure'),
|
||||
'text': _('Configure')},
|
||||
{'url': reverse_lazy('dynamicDNS:statuspage'),
|
||||
'text': _('Status')}
|
||||
]
|
||||
|
||||
def init():
|
||||
"""Initialize the dynamicDNS module"""
|
||||
menu = cfg.main_menu.get('apps:index')
|
||||
menu.add_urlname('dynamicDNS', 'glyphicon-comment', 'dynamicDNS:index', 40)
|
||||
|
||||
@login_required
|
||||
def index(request):
|
||||
"""Serve dynamic DNS page"""
|
||||
|
||||
is_installed = actions.run('dynamicDNS', ['get-installed']).strip() == 'installed'
|
||||
|
||||
if is_installed:
|
||||
index_subsubmenu = subsubmenu
|
||||
else:
|
||||
index_subsubmenu = None
|
||||
|
||||
return TemplateResponse(request, 'dynamicDNS.html',
|
||||
{'title': _('dynamicDNS'),
|
||||
'is_installed': is_installed,
|
||||
'subsubmenu': index_subsubmenu})
|
||||
|
||||
class TrimmedCharField(forms.CharField):
|
||||
"""Trim the contents of a CharField"""
|
||||
def clean(self, value):
|
||||
"""Clean and validate the field value"""
|
||||
if value:
|
||||
value = value.strip()
|
||||
|
||||
return super(TrimmedCharField, self).clean(value)
|
||||
|
||||
class ConfigureForm(forms.Form):
|
||||
"""Form to configure the dynamic DNS client"""
|
||||
enabled = forms.BooleanField(label=_('Enable dynamicDNS'),
|
||||
required=False)
|
||||
|
||||
dynamicDNS_Server = TrimmedCharField(
|
||||
label=_('Server Address'),
|
||||
help_text=_('Example: gnudip.provider.org'),
|
||||
validators=[
|
||||
validators.RegexValidator(r'^[\w-]{1,63}(\.[\w-]{1,63})*$',
|
||||
_('Invalid server name'))])
|
||||
|
||||
dynamicDNS_Domain = TrimmedCharField(
|
||||
label=_('Domain Name'),
|
||||
help_text=_('Example: hostname.sds-ip.de'),
|
||||
validators=[
|
||||
validators.RegexValidator(r'^[\w-]{1,63}(\.[\w-]{1,63})*$',
|
||||
_('Invalid domain name'))])
|
||||
|
||||
dynamicDNS_User = TrimmedCharField(
|
||||
label=_('Username'),
|
||||
help_text=_('You should have been requested to select a username when you created the account'))
|
||||
|
||||
dynamicDNS_Secret = TrimmedCharField(
|
||||
label=_('Password'), widget=forms.PasswordInput(),
|
||||
required=False,
|
||||
help_text=_('You should have been requested to select a password when you created the account. \
|
||||
If you left this field empty your password will be unchanged.'))
|
||||
|
||||
dynamicDNS_Secret_repeat = TrimmedCharField(
|
||||
label=_('repeat Password'), widget=forms.PasswordInput(),
|
||||
required=False,
|
||||
help_text=_('insert the password twice to avoid typos. If you left this field empty your password \
|
||||
will be unchanged.'),)
|
||||
|
||||
dynamicDNS_IPURL = TrimmedCharField(
|
||||
label=_('IP check URL'),
|
||||
required=False,
|
||||
help_text=_('Optional Value. If your FreedomBox is not connected directly to the Internet (i.e. \
|
||||
connected to a NAT router) this URL is used to figure out the real Internet IP. The URL should \
|
||||
simply return the IP where the client comes from. Example: http://myip.datasystems24.de'),
|
||||
validators=[
|
||||
validators.URLValidator(schemes=['http','https','ftp'])])
|
||||
|
||||
@login_required
|
||||
def configure(request):
|
||||
"""Serve the configuration form"""
|
||||
status = get_status()
|
||||
form = None
|
||||
|
||||
if request.method == 'POST':
|
||||
form = ConfigureForm(request.POST, prefix='dynamicDNS')
|
||||
if form.is_valid():
|
||||
_apply_changes(request, status, form.cleaned_data)
|
||||
status = get_status()
|
||||
form = ConfigureForm(initial=status, prefix='dynamicDNS')
|
||||
else:
|
||||
form = ConfigureForm(initial=status, prefix='dynamicDNS')
|
||||
|
||||
return TemplateResponse(request, 'dynamicDNS_configure.html',
|
||||
{'title': _('Configure dynamicDNS Client'),
|
||||
'form': form,
|
||||
'subsubmenu': subsubmenu})
|
||||
|
||||
@login_required
|
||||
def statuspage(request):
|
||||
"""Serve the status page """
|
||||
check_NAT = actions.run('dynamicDNS', ['get-nat'])
|
||||
last_update = actions.run('dynamicDNS', ['get-last-success'])
|
||||
|
||||
no_NAT = check_NAT.strip() == 'no'
|
||||
NAT_unchecked = check_NAT.strip() == 'unknown'
|
||||
timer = actions.run('dynamicDNS', ['get-timer'])
|
||||
|
||||
if no_NAT:
|
||||
LOGGER.info('we are not behind a NAT')
|
||||
|
||||
if NAT_unchecked:
|
||||
LOGGER.info('we did not checked if we are behind a NAT')
|
||||
|
||||
return TemplateResponse(request, 'dynamicDNS_status.html',
|
||||
{'title': _('Status of dynamicDNS Client'),
|
||||
'no_NAT': no_NAT,
|
||||
'NAT_unchecked' : NAT_unchecked,
|
||||
'timer' : timer,
|
||||
'last_update' : last_update,
|
||||
'subsubmenu': subsubmenu})
|
||||
|
||||
def get_status():
|
||||
"""Return the current status"""
|
||||
"""ToDo: use key/value instead of hard coded value list"""
|
||||
status = {}
|
||||
output = actions.run('dynamicDNS', 'status')
|
||||
details = output.split()
|
||||
status['enabled'] = (output.split()[0] == 'enabled')
|
||||
if len(details) > 1:
|
||||
status['dynamicDNS_Server'] = details[1]
|
||||
else:
|
||||
status['dynamicDNS_Server'] = ''
|
||||
|
||||
if len(details) > 2:
|
||||
status['dynamicDNS_Domain'] = details[2]
|
||||
else:
|
||||
status['dynamicDNS_Domain'] = ''
|
||||
|
||||
if len(details) > 3:
|
||||
status['dynamicDNS_User'] = details[3]
|
||||
else:
|
||||
status['dynamicDNS_User'] = ''
|
||||
|
||||
if len(details) > 4:
|
||||
status['dynamicDNS_Secret'] = details[4]
|
||||
else:
|
||||
status['dynamicDNS_Secret'] = ''
|
||||
|
||||
if len(details) > 5:
|
||||
status['dynamicDNS_IPURL'] = details[5]
|
||||
else:
|
||||
status['dynamicDNS_Secret'] = ''
|
||||
|
||||
return status
|
||||
|
||||
def _apply_changes(request, old_status, new_status):
|
||||
"""Apply the changes to Dynamic DNS client"""
|
||||
LOGGER.info('New status is - %s', new_status)
|
||||
LOGGER.info('Old status was - %s', old_status)
|
||||
FAIL = False
|
||||
|
||||
if new_status['dynamicDNS_Secret_repeat'] != new_status['dynamicDNS_Secret']:
|
||||
messages.error(request, _('passwords does not match'))
|
||||
FAIL = True
|
||||
|
||||
if old_status['dynamicDNS_Secret'] == '' and new_status['dynamicDNS_Secret'] == '':
|
||||
messages.error(request, _('please give a password'))
|
||||
FAIL = True
|
||||
|
||||
if False == FAIL:
|
||||
if new_status['dynamicDNS_Secret'] == '':
|
||||
new_status['dynamicDNS_Secret'] = old_status['dynamicDNS_Secret']
|
||||
|
||||
if new_status['dynamicDNS_IPURL'] == '':
|
||||
new_status['dynamicDNS_IPURL'] = 'none'
|
||||
|
||||
if old_status['dynamicDNS_Server'] != new_status['dynamicDNS_Server'] or \
|
||||
old_status['dynamicDNS_Domain'] != new_status['dynamicDNS_Domain'] or \
|
||||
old_status['dynamicDNS_User'] != new_status['dynamicDNS_User'] or \
|
||||
old_status['dynamicDNS_Secret'] != new_status['dynamicDNS_Secret'] or \
|
||||
old_status['dynamicDNS_IPURL'] != new_status['dynamicDNS_IPURL']:
|
||||
|
||||
_run(['configure', '-s', new_status['dynamicDNS_Server'],
|
||||
'-d', new_status['dynamicDNS_Domain'],
|
||||
'-u', new_status['dynamicDNS_User'],
|
||||
'-p', new_status['dynamicDNS_Secret'],
|
||||
'-I', new_status['dynamicDNS_IPURL']])
|
||||
_run(['stop'])
|
||||
_run(['start'])
|
||||
messages.success(request, _('Dynamic DNS configuration is updated!'))
|
||||
|
||||
if old_status['enabled'] != new_status['enabled']:
|
||||
if new_status['enabled']:
|
||||
_run(['start'])
|
||||
messages.success(request, _('Dynamic DNS is enabled now!'))
|
||||
else:
|
||||
_run(['stop'])
|
||||
messages.success(request, _('Dynamic DNS is disabled now!'))
|
||||
else:
|
||||
messages.error(request, _('At least on failure occured, please check your input.'))
|
||||
|
||||
def _run(arguments, superuser=False):
|
||||
"""Run a given command and raise exception if there was an error"""
|
||||
command = 'dynamicDNS'
|
||||
|
||||
if superuser:
|
||||
return actions.superuser_run(command, arguments)
|
||||
else:
|
||||
return actions.run(command, arguments)
|
||||
42
plinth/modules/dynamicDNS/templates/dynamicDNS.html
Normal file
42
plinth/modules/dynamicDNS/templates/dynamicDNS.html
Normal file
@ -0,0 +1,42 @@
|
||||
{% extends "base.html" %}
|
||||
{% comment %}
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
{% endcomment %}
|
||||
|
||||
{% load bootstrap %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
{% if is_installed %}
|
||||
|
||||
<p>If your internet provider changes your IP address periodic (i.e. every 24h) it may be hard for others to find you in the WEB. And for this reason nobody may find the services which are provided by freedombox (like your owncloud). The solution is to assign a DNS name to your IP address and update the DNS name every time your IP is changed by your Internet provider. Dynamic DNS allows you to push your current public IP address to an <a href='http://gnudip2.sourceforge.net/'
|
||||
target='_blank'> gnudip </a> server. Afterwards the Server will assign your personal DNS name with the new IP and if someone from the internet asks for your DNS name he will get your personal IP answered.</p>
|
||||
|
||||
{% else %}
|
||||
|
||||
<h2>DynamicDNS client</h2>
|
||||
|
||||
<p>The Dynamic DNS tool <i>ez-ipupdate</i> is not installed.</p>
|
||||
|
||||
<p>ez-ipupdate comes pre-installed with {{ cfg.box_name }}. On any Debian-based
|
||||
system (such as {{ cfg.box_name }}) you may install it using the command
|
||||
<code>apt-get install ez-ipupdate</code>.</p>
|
||||
|
||||
{% endif %}
|
||||
|
||||
{% endblock %}
|
||||
@ -0,0 +1,34 @@
|
||||
{% extends "base.html" %}
|
||||
{% comment %}
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
{% endcomment %}
|
||||
|
||||
{% load bootstrap %}
|
||||
|
||||
{% block content %}
|
||||
<h3>Configuration</h3>
|
||||
<form class="form" method="post">
|
||||
{% csrf_token %}
|
||||
|
||||
{{ form|bootstrap }}
|
||||
|
||||
<input type="submit" class="btn btn-primary btn-md" value="Update setup"/>
|
||||
|
||||
</form>
|
||||
|
||||
{% endblock %}
|
||||
42
plinth/modules/dynamicDNS/templates/dynamicDNS_status.html
Executable file
42
plinth/modules/dynamicDNS/templates/dynamicDNS_status.html
Executable file
@ -0,0 +1,42 @@
|
||||
{% extends "base.html" %}
|
||||
{% comment %}
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
{% endcomment %}
|
||||
|
||||
{% load bootstrap %}
|
||||
|
||||
{% block content %}
|
||||
<p>
|
||||
<h3>NAT type</h3>
|
||||
{% if NAT_unchecked %}
|
||||
NAT type not detected yet, if you do not provide a "IP check URL" we will
|
||||
not detect a NAT type.
|
||||
{% else %}
|
||||
{% if no_NAT %}
|
||||
Direct connection to the internet.
|
||||
{% else %}
|
||||
Behind NAT, this means that dynamic DNS service will poll the
|
||||
"IP check URL" for changes (we need the "IP check URL" for this reason - otherwise we will not detect IP changes).
|
||||
It may take up to {{ timer }} minutes until we update your DNS entry in case of WAN IP change.
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
<h3>Last update</h3>
|
||||
{{ last_update }}
|
||||
</p>
|
||||
|
||||
{% endblock %}
|
||||
30
plinth/modules/dynamicDNS/urls.py
Normal file
30
plinth/modules/dynamicDNS/urls.py
Normal file
@ -0,0 +1,30 @@
|
||||
#
|
||||
# This file is part of Plinth.
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
|
||||
"""
|
||||
URLs for the DynamicDNS module
|
||||
"""
|
||||
|
||||
from django.conf.urls import patterns, url
|
||||
|
||||
|
||||
urlpatterns = patterns(
|
||||
'plinth.modules.dynamicDNS.dynamicDNS',
|
||||
url(r'^apps/dynamicDNS/$', 'index', name='index'),
|
||||
url(r'^apps/dynamicDNS/configure/$', 'configure', name='configure'),
|
||||
url(r'^apps/dynamicDNS/statuspage/$', 'statuspage', name='statuspage')
|
||||
)
|
||||
Loading…
x
Reference in New Issue
Block a user