mirror of
https://github.com/YunoHost/yunohost.git
synced 2024-09-03 20:06:10 +02:00
Remove old 'tools diagnosis', superseded by the new diagnosis system
This commit is contained in:
parent
47c7c72455
commit
94f3557aeb
2 changed files with 3 additions and 195 deletions
|
@ -1606,16 +1606,6 @@ tools:
|
|||
help: Upgrade only the system packages
|
||||
action: store_true
|
||||
|
||||
### tools_diagnosis()
|
||||
diagnosis:
|
||||
action_help: YunoHost diagnosis
|
||||
api: GET /diagnosis
|
||||
arguments:
|
||||
-p:
|
||||
full: --private
|
||||
help: Show private data (domain, IP)
|
||||
action: store_true
|
||||
|
||||
### tools_port_available()
|
||||
port-available:
|
||||
action_help: Check availability of a local port
|
||||
|
|
|
@ -30,23 +30,19 @@ import json
|
|||
import subprocess
|
||||
import pwd
|
||||
import socket
|
||||
from xmlrpclib import Fault
|
||||
from importlib import import_module
|
||||
from collections import OrderedDict
|
||||
|
||||
from moulinette import msignals, m18n
|
||||
from moulinette.utils.log import getActionLogger
|
||||
from moulinette.utils.process import check_output, call_async_output
|
||||
from moulinette.utils.filesystem import read_json, write_to_json, read_yaml, write_to_yaml
|
||||
from yunohost.app import app_fetchlist, app_info, app_upgrade, app_ssowatconf, app_list, _install_appslist_fetch_cron
|
||||
from yunohost.app import app_fetchlist, app_info, app_upgrade, app_ssowatconf, _install_appslist_fetch_cron
|
||||
from yunohost.domain import domain_add, domain_list, _get_maindomain, _set_maindomain
|
||||
from yunohost.dyndns import _dyndns_available, _dyndns_provides
|
||||
from yunohost.firewall import firewall_upnp
|
||||
from yunohost.service import service_status, service_start, service_enable
|
||||
from yunohost.service import service_start, service_enable
|
||||
from yunohost.regenconf import regen_conf
|
||||
from yunohost.monitor import monitor_disk, monitor_system
|
||||
from yunohost.utils.packages import ynh_packages_version, _dump_sources_list, _list_upgradable_apt_packages
|
||||
from yunohost.utils.network import get_public_ip
|
||||
from yunohost.utils.packages import _dump_sources_list, _list_upgradable_apt_packages
|
||||
from yunohost.utils.error import YunohostError
|
||||
from yunohost.log import is_unit_operation, OperationLogger
|
||||
|
||||
|
@ -726,184 +722,6 @@ def tools_upgrade(operation_logger, apps=None, system=False):
|
|||
operation_logger.success()
|
||||
|
||||
|
||||
def tools_diagnosis(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()
|
||||
|
||||
diagnosis["backports"] = check_output("dpkg -l |awk '/^ii/ && $3 ~ /bpo[6-8]/ {print $2}'").split()
|
||||
|
||||
# Server basic monitoring
|
||||
diagnosis['system'] = OrderedDict()
|
||||
try:
|
||||
disks = monitor_disk(units=['filesystem'], human_readable=True)
|
||||
except (YunohostError, Fault) as e:
|
||||
logger.warning(m18n.n('diagnosis_monitor_disk_error', error=format(e)), exc_info=1)
|
||||
else:
|
||||
diagnosis['system']['disks'] = {}
|
||||
for disk in disks:
|
||||
if isinstance(disks[disk], str):
|
||||
diagnosis['system']['disks'][disk] = disks[disk]
|
||||
else:
|
||||
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 YunohostError 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']),
|
||||
}
|
||||
|
||||
# nginx -t
|
||||
p = subprocess.Popen("nginx -t".split(),
|
||||
stdout=subprocess.PIPE,
|
||||
stderr=subprocess.STDOUT)
|
||||
out, _ = p.communicate()
|
||||
diagnosis["nginx"] = out.strip().split("\n")
|
||||
if p.returncode != 0:
|
||||
logger.error(out)
|
||||
|
||||
# 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 YunohostError 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'] = {}
|
||||
diagnosis['private']['public_ip']['IPv4'] = get_public_ip(4)
|
||||
diagnosis['private']['public_ip']['IPv6'] = get_public_ip(6)
|
||||
|
||||
# Domains
|
||||
diagnosis['private']['domains'] = domain_list()['domains']
|
||||
|
||||
diagnosis['private']['regen_conf'] = regen_conf(with_diff=True, dry_run=True)
|
||||
|
||||
try:
|
||||
diagnosis['security'] = {
|
||||
"CVE-2017-5754": {
|
||||
"name": "meltdown",
|
||||
"vulnerable": _check_if_vulnerable_to_meltdown(),
|
||||
}
|
||||
}
|
||||
except Exception as e:
|
||||
import traceback
|
||||
traceback.print_exc()
|
||||
logger.warning("Unable to check for meltdown vulnerability: %s" % e)
|
||||
|
||||
return diagnosis
|
||||
|
||||
|
||||
def _check_if_vulnerable_to_meltdown():
|
||||
# meltdown CVE: https://security-tracker.debian.org/tracker/CVE-2017-5754
|
||||
|
||||
# We use a cache file to avoid re-running the script so many times,
|
||||
# which can be expensive (up to around 5 seconds on ARM)
|
||||
# and make the admin appear to be slow (c.f. the calls to diagnosis
|
||||
# from the webadmin)
|
||||
#
|
||||
# The cache is in /tmp and shall disappear upon reboot
|
||||
# *or* we compare it to dpkg.log modification time
|
||||
# such that it's re-ran if there was package upgrades
|
||||
# (e.g. from yunohost)
|
||||
cache_file = "/tmp/yunohost-meltdown-diagnosis"
|
||||
dpkg_log = "/var/log/dpkg.log"
|
||||
if os.path.exists(cache_file):
|
||||
if not os.path.exists(dpkg_log) or os.path.getmtime(cache_file) > os.path.getmtime(dpkg_log):
|
||||
logger.debug("Using cached results for meltdown checker, from %s" % cache_file)
|
||||
return read_json(cache_file)[0]["VULNERABLE"]
|
||||
|
||||
# script taken from https://github.com/speed47/spectre-meltdown-checker
|
||||
# script commit id is store directly in the script
|
||||
file_dir = os.path.split(__file__)[0]
|
||||
SCRIPT_PATH = os.path.join(file_dir, "./vendor/spectre-meltdown-checker/spectre-meltdown-checker.sh")
|
||||
|
||||
# '--variant 3' corresponds to Meltdown
|
||||
# example output from the script:
|
||||
# [{"NAME":"MELTDOWN","CVE":"CVE-2017-5754","VULNERABLE":false,"INFOS":"PTI mitigates the vulnerability"}]
|
||||
try:
|
||||
logger.debug("Running meltdown vulnerability checker")
|
||||
call = subprocess.Popen("bash %s --batch json --variant 3" %
|
||||
SCRIPT_PATH, shell=True,
|
||||
stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE)
|
||||
|
||||
# TODO / FIXME : here we are ignoring error messages ...
|
||||
# in particular on RPi2 and other hardware, the script complains about
|
||||
# "missing some kernel info (see -v), accuracy might be reduced"
|
||||
# Dunno what to do about that but we probably don't want to harass
|
||||
# users with this warning ...
|
||||
output, err = call.communicate()
|
||||
assert call.returncode in (0, 2, 3), "Return code: %s" % call.returncode
|
||||
|
||||
# If there are multiple lines, sounds like there was some messages
|
||||
# in stdout that are not json >.> ... Try to get the actual json
|
||||
# stuff which should be the last line
|
||||
output = output.strip()
|
||||
if "\n" in output:
|
||||
logger.debug("Original meltdown checker output : %s" % output)
|
||||
output = output.split("\n")[-1]
|
||||
|
||||
CVEs = json.loads(output)
|
||||
assert len(CVEs) == 1
|
||||
assert CVEs[0]["NAME"] == "MELTDOWN"
|
||||
except Exception as e:
|
||||
import traceback
|
||||
traceback.print_exc()
|
||||
logger.warning("Something wrong happened when trying to diagnose Meltdown vunerability, exception: %s" % e)
|
||||
raise Exception("Command output for failed meltdown check: '%s'" % output)
|
||||
|
||||
logger.debug("Writing results from meltdown checker to cache file, %s" % cache_file)
|
||||
write_to_json(cache_file, CVEs)
|
||||
return CVEs[0]["VULNERABLE"]
|
||||
|
||||
|
||||
def tools_port_available(port):
|
||||
"""
|
||||
Check availability of a local port
|
||||
|
|
Loading…
Add table
Reference in a new issue