def dyndns_update(dyn_host="dyndns.yunohost.org", domain=None, key=None, ipv4=None, ipv6=None): """ Update IP on DynDNS platform Keyword argument: domain -- Full domain to update dyn_host -- Dynette DNS server to inform key -- Public DNS key ipv4 -- IP address to send ipv6 -- IPv6 address to send """ # IPv4 if ipv4 is None: ipv4 = get_public_ip() try: with open('/etc/yunohost/dyndns/old_ip', 'r') as f: old_ip = f.readline().rstrip() except IOError: old_ip = '0.0.0.0' # IPv6 if ipv6 is None: try: ip_route_out = subprocess.check_output( ['ip', 'route', 'get', '2000::']).split('\n') if len(ip_route_out) > 0: route = IPRouteLine(ip_route_out[0]) if not route.unreachable: ipv6 = route.src_addr except (OSError, ValueError) as e: # Unlikely case "ip route" does not return status 0 # or produces unexpected output raise MoulinetteError(errno.EBADMSG, "ip route cmd error : {}".format(e)) if ipv6 is None: logger.info(m18n.n('no_ipv6_connectivity')) try: with open('/etc/yunohost/dyndns/old_ipv6', 'r') as f: old_ipv6 = f.readline().rstrip() except IOError: old_ipv6 = '0000:0000:0000:0000:0000:0000:0000:0000' if old_ip != ipv4 or old_ipv6 != ipv6: if domain is None: # Retrieve the first registered domain for path in glob.iglob('/etc/yunohost/dyndns/K*.private'): match = re_dyndns_private_key.match(path) if not match: continue _domain = match.group('domain') try: # Check if domain is registered if requests.get('https://{0}/test/{1}'.format( dyn_host, _domain)).status_code == 200: continue except requests.ConnectionError: raise MoulinetteError(errno.ENETUNREACH, m18n.n('no_internet_connection')) domain = _domain key = path break if not domain: raise MoulinetteError(errno.EINVAL, m18n.n('dyndns_no_domain_registered')) if key is None: keys = glob.glob( '/etc/yunohost/dyndns/K{0}.+*.private'.format(domain)) if len(keys) > 0: key = keys[0] if not key: raise MoulinetteError(errno.EIO, m18n.n('dyndns_key_not_found')) host = domain.split('.')[1:] host = '.'.join(host) lines = [ 'server %s' % dyn_host, 'zone %s' % host, 'update delete %s. A' % domain, 'update delete %s. AAAA' % domain, 'update delete %s. MX' % domain, 'update delete %s. TXT' % domain, 'update delete pubsub.%s. A' % domain, 'update delete pubsub.%s. AAAA' % domain, 'update delete muc.%s. A' % domain, 'update delete muc.%s. AAAA' % domain, 'update delete vjud.%s. A' % domain, 'update delete vjud.%s. AAAA' % domain, 'update delete _xmpp-client._tcp.%s. SRV' % domain, 'update delete _xmpp-server._tcp.%s. SRV' % domain, 'update add %s. 1800 A %s' % (domain, ipv4), 'update add %s. 14400 MX 5 %s.' % (domain, domain), 'update add %s. 14400 TXT "v=spf1 a mx -all"' % domain, 'update add pubsub.%s. 1800 A %s' % (domain, ipv4), 'update add muc.%s. 1800 A %s' % (domain, ipv4), 'update add vjud.%s. 1800 A %s' % (domain, ipv4), 'update add _xmpp-client._tcp.%s. 14400 SRV 0 5 5222 %s.' % (domain, domain), 'update add _xmpp-server._tcp.%s. 14400 SRV 0 5 5269 %s.' % (domain, domain) ] if ipv6 is not None: lines += [ 'update add %s. 1800 AAAA %s' % (domain, ipv6), 'update add pubsub.%s. 1800 AAAA %s' % (domain, ipv6), 'update add muc.%s. 1800 AAAA %s' % (domain, ipv6), 'update add vjud.%s. 1800 AAAA %s' % (domain, ipv6), ] lines += [ 'show', 'send' ] with open('/etc/yunohost/dyndns/zone', 'w') as zone: for line in lines: zone.write(line + '\n') if os.system('/usr/bin/nsupdate -k %s /etc/yunohost/dyndns/zone' % key) == 0: logger.success(m18n.n('dyndns_ip_updated')) with open('/etc/yunohost/dyndns/old_ip', 'w') as f: f.write(ipv4) if ipv6 is not None: with open('/etc/yunohost/dyndns/old_ipv6', 'w') as f: f.write(ipv6) else: os.system('rm -f /etc/yunohost/dyndns/old_ip') os.system('rm -f /etc/yunohost/dyndns/old_ipv6') raise MoulinetteError(errno.EPERM, m18n.n('dyndns_ip_update_failed'))
def monitor_network(units=None, human_readable=False): """ Monitor network interfaces Keyword argument: units -- Unit(s) to monitor human_readable -- Print sizes in human readable format """ glances = _get_glances_api() result = {} if units is None: units = ['check', 'usage', 'infos'] # Get network devices and their addresses devices = {} output = subprocess.check_output('ip addr show'.split()) for d in re.split('^(?:[0-9]+: )', output, flags=re.MULTILINE): # Extract device name (1) and its addresses (2) m = re.match('([^\s@]+)(?:@[\S]+)?: (.*)', d, flags=re.DOTALL) if m: devices[m.group(1)] = m.group(2) # Retrieve monitoring for unit(s) for u in units: if u == 'check': result[u] = {} with open('/etc/yunohost/current_host', 'r') as f: domain = f.readline().rstrip() cmd_check_smtp = os.system('/bin/nc -z -w1 yunohost.org 25') if cmd_check_smtp == 0: smtp_check = m18n.n('network_check_smtp_ok') else: smtp_check = m18n.n('network_check_smtp_ko') try: answers = dns.resolver.query(domain, 'MX') mx_check = {} i = 0 for server in answers: mx_id = 'mx%s' % i mx_check[mx_id] = server i = i + 1 except: mx_check = m18n.n('network_check_mx_ko') result[u] = {'smtp_check': smtp_check, 'mx_check': mx_check} elif u == 'usage': result[u] = {} for i in json.loads(glances.getNetwork()): iname = i['interface_name'] if iname in devices.keys(): del i['interface_name'] if human_readable: for k in i.keys(): if k != 'time_since_update': i[k] = binary_to_human(i[k]) + 'B' result[u][iname] = i else: logger.debug('interface name %s was not found', iname) elif u == 'infos': try: p_ipv4 = get_public_ip() except: p_ipv4 = 'unknown' l_ip = 'unknown' for name, addrs in devices.items(): if name == 'lo': continue if not isinstance(l_ip, dict): l_ip = {} l_ip[name] = _extract_inet(addrs) gateway = 'unknown' output = subprocess.check_output('ip route show'.split()) m = re.search('default via (.*) dev ([a-z]+[0-9]?)', output) if m: addr = _extract_inet(m.group(1), True) if len(addr) == 1: proto, gateway = addr.popitem() result[u] = { 'public_ip': p_ipv4, 'local_ip': l_ip, 'gateway': gateway, } else: raise MoulinetteError(errno.EINVAL, m18n.n('unit_unknown', unit=u)) if len(units) == 1: return result[units[0]] return result
def monitor_network(units=None, human_readable=False): """ Monitor network interfaces Keyword argument: units -- Unit(s) to monitor human_readable -- Print sizes in human readable format """ glances = _get_glances_api() result = {} if units is None: units = ['check', 'usage', 'infos'] # Get network devices and their addresses devices = {} output = subprocess.check_output('ip addr show'.split()) for d in re.split('^(?:[0-9]+: )', output, flags=re.MULTILINE): # Extract device name (1) and its addresses (2) m = re.match('([^\s@]+)(?:@[\S]+)?: (.*)', d, flags=re.DOTALL) if m: devices[m.group(1)] = m.group(2) # Retrieve monitoring for unit(s) for u in units: if u == 'check': result[u] = {} with open('/etc/yunohost/current_host', 'r') as f: domain = f.readline().rstrip() cmd_check_smtp = os.system('/bin/nc -z -w1 yunohost.org 25') if cmd_check_smtp == 0: smtp_check = m18n.n('network_check_smtp_ok') else: smtp_check = m18n.n('network_check_smtp_ko') try: answers = dns.resolver.query(domain,'MX') mx_check = {} i = 0 for server in answers: mx_id = 'mx%s' %i mx_check[mx_id] = server i = i + 1 except: mx_check = m18n.n('network_check_mx_ko') result[u] = { 'smtp_check': smtp_check, 'mx_check': mx_check } elif u == 'usage': result[u] = {} for i in json.loads(glances.getNetwork()): iname = i['interface_name'] if iname in devices.keys(): del i['interface_name'] if human_readable: for k in i.keys(): if k != 'time_since_update': i[k] = binary_to_human(i[k]) + 'B' result[u][iname] = i else: logger.debug('interface name %s was not found', iname) elif u == 'infos': try: p_ipv4 = get_public_ip() except: p_ipv4 = 'unknown' l_ip = 'unknown' for name, addrs in devices.items(): if name == 'lo': continue if not isinstance(l_ip, dict): l_ip = {} l_ip[name] = _extract_inet(addrs) gateway = 'unknown' output = subprocess.check_output('ip route show'.split()) m = re.search('default via (.*) dev ([a-z]+[0-9]?)', output) if m: addr = _extract_inet(m.group(1), True) if len(addr) == 1: proto, gateway = addr.popitem() result[u] = { 'public_ip': p_ipv4, 'local_ip': l_ip, 'gateway': gateway, } else: raise MoulinetteError(errno.EINVAL, m18n.n('unit_unknown', unit=u)) if len(units) == 1: return result[units[0]] return result
def tools_diagnosis(auth, private=False): """ Return global info about current yunohost instance to help debugging """ diagnosis = OrderedDict() # Debian release try: with open('/etc/debian_version', 'r') as f: debian_version = f.read().rstrip() except IOError as e: logger.warning(m18n.n('diagnosis_debian_version_error', error=format(e)), exc_info=1) else: diagnosis['host'] = "Debian %s" % debian_version # Kernel version try: with open('/proc/sys/kernel/osrelease', 'r') as f: kernel_version = f.read().rstrip() except IOError as e: logger.warning(m18n.n('diagnosis_kernel_version_error', error=format(e)), exc_info=1) else: diagnosis['kernel'] = kernel_version # Packages version diagnosis['packages'] = ynh_packages_version() # Server basic monitoring diagnosis['system'] = OrderedDict() try: disks = monitor_disk(units=['filesystem'], human_readable=True) except MoulinetteError as e: logger.warning(m18n.n('diagnosis_monitor_disk_error', error=format(e)), exc_info=1) else: diagnosis['system']['disks'] = {} for disk in disks: diagnosis['system']['disks'][ disk] = 'Mounted on %s, %s (%s free)' % ( disks[disk]['mnt_point'], disks[disk]['size'], disks[disk]['avail']) try: system = monitor_system(units=['cpu', 'memory'], human_readable=True) except MoulinetteError as e: logger.warning(m18n.n('diagnosis_monitor_system_error', error=format(e)), exc_info=1) else: diagnosis['system']['memory'] = { 'ram': '%s (%s free)' % (system['memory']['ram']['total'], system['memory']['ram']['free']), 'swap': '%s (%s free)' % (system['memory']['swap']['total'], system['memory']['swap']['free']), } # Services status services = service_status() diagnosis['services'] = {} for service in services: diagnosis['services'][service] = "%s (%s)" % ( services[service]['status'], services[service]['loaded']) # YNH Applications try: applications = app_list()['apps'] except MoulinetteError as e: diagnosis['applications'] = m18n.n('diagnosis_no_apps') else: diagnosis['applications'] = {} for application in applications: if application['installed']: diagnosis['applications'][application['id']] = application[ 'label'] if application['label'] else application['name'] # Private data if private: diagnosis['private'] = OrderedDict() # Public IP diagnosis['private']['public_ip'] = {} try: diagnosis['private']['public_ip']['IPv4'] = get_public_ip(4) except MoulinetteError as e: pass try: diagnosis['private']['public_ip']['IPv6'] = get_public_ip(6) except MoulinetteError as e: pass # Domains diagnosis['private']['domains'] = domain_list(auth)['domains'] return diagnosis
def tools_diagnosis(auth, private=False): """ Return global info about current yunohost instance to help debugging """ diagnosis = OrderedDict(); # Debian release try: with open('/etc/debian_version', 'r') as f: debian_version = f.read().rstrip() except IOError as e: logger.warning(m18n.n('diagnosis_debian_version_error', error=format(e)), exc_info=1) else: diagnosis['host'] = "Debian %s" % debian_version # Kernel version try: with open('/proc/sys/kernel/osrelease', 'r') as f: kernel_version = f.read().rstrip() except IOError as e: logger.warning(m18n.n('diagnosis_kernel_version_error', error=format(e)), exc_info=1) else: diagnosis['kernel'] = kernel_version # Packages version diagnosis['packages'] = ynh_packages_version() # Server basic monitoring diagnosis['system'] = OrderedDict() try: disks = monitor_disk(units=['filesystem'], human_readable=True) except MoulinetteError as e: logger.warning(m18n.n('diagnosis_monitor_disk_error', error=format(e)), exc_info=1) else: diagnosis['system']['disks'] = {} for disk in disks: diagnosis['system']['disks'][disk] = 'Mounted on %s, %s (%s free)' % ( disks[disk]['mnt_point'], disks[disk]['size'], disks[disk]['avail'] ) try: system = monitor_system(units=['cpu', 'memory'], human_readable=True) except MoulinetteError as e: logger.warning(m18n.n('diagnosis_monitor_system_error', error=format(e)), exc_info=1) else: diagnosis['system']['memory'] = { 'ram' : '%s (%s free)' % (system['memory']['ram']['total'], system['memory']['ram']['free']), 'swap' : '%s (%s free)' % (system['memory']['swap']['total'], system['memory']['swap']['free']), } # Services status services = service_status() diagnosis['services'] = {} for service in services: diagnosis['services'][service] = "%s (%s)" % (services[service]['status'], services[service]['loaded']) # YNH Applications try: applications = app_list()['apps'] except MoulinetteError as e: diagnosis['applications'] = m18n.n('diagnosis_no_apps') else: diagnosis['applications'] = {} for application in applications: if application['installed']: diagnosis['applications'][application['id']] = application['label'] if application['label'] else application['name'] # Private data if private: diagnosis['private'] = OrderedDict() # Public IP diagnosis['private']['public_ip'] = {} try: diagnosis['private']['public_ip']['IPv4'] = get_public_ip(4) except MoulinetteError as e: pass try: diagnosis['private']['public_ip']['IPv6'] = get_public_ip(6) except MoulinetteError as e: pass # Domains diagnosis['private']['domains'] = domain_list(auth)['domains'] return diagnosis