From 39d411be5b3a1976e0f2b2f07a0f6704fca66458 Mon Sep 17 00:00:00 2001 From: James Valleroy Date: Mon, 28 Jun 2021 16:53:56 -0400 Subject: [PATCH] upgrades: Check for held freedombox package daily Guard against removing a hold while the package manager is busy. Test: 1. Place hold on freedombox package. 2. Wait 3 minutes in development mode. - Package is held. 3. Touch /var/lib/freedombox/package-held. 4. Wait 3 minutes in development mode. - Package is not held. - Flag is removed. Signed-off-by: James Valleroy --- actions/packages | 15 ++++++--------- actions/upgrades | 11 ++++++++--- plinth/action_utils.py | 12 ++++++++++++ 3 files changed, 26 insertions(+), 12 deletions(-) diff --git a/actions/packages b/actions/packages index ff15e9df6..d9415f5eb 100755 --- a/actions/packages +++ b/actions/packages @@ -18,9 +18,8 @@ import apt.cache import apt_inst import apt_pkg from plinth import cfg -from plinth.action_utils import apt_hold_freedombox, run_apt_command - -LOCK_FILE = '/var/lib/dpkg/lock' +from plinth.action_utils import (apt_hold_freedombox, is_package_manager_busy, + run_apt_command) logger = logging.getLogger(__name__) @@ -115,12 +114,10 @@ def _assert_managed_packages(module, packages): def subcommand_is_package_manager_busy(_): - """Return whether package manager is busy. - This command uses the `lsof` command to check whether the dpkg lock file - is open which indicates that the package manager is busy""" - try: - subprocess.check_output(['lsof', LOCK_FILE]) - except subprocess.CalledProcessError: + """Check whether package manager is busy. + + An exit code of zero indicates that package manager is busy.""" + if not is_package_manager_busy(): sys.exit(-1) diff --git a/actions/upgrades b/actions/upgrades index 313adcf45..5278c403c 100755 --- a/actions/upgrades +++ b/actions/upgrades @@ -16,8 +16,8 @@ import time from plinth.action_utils import (apt_hold, apt_hold_flag, apt_hold_freedombox, apt_unhold_freedombox, debconf_set_selections, - run_apt_command, service_daemon_reload, - service_restart) + is_package_manager_busy, run_apt_command, + service_daemon_reload, service_restart) from plinth.modules.apache.components import check_url from plinth.modules.snapshot import (is_apt_snapshots_enabled, is_supported as snapshot_is_supported, load_augeas as @@ -145,7 +145,7 @@ def _run(): # In case freedombox package was left in held state by an # interrupted process, release it. - if apt_hold_flag.exists(): + if apt_hold_flag.exists() and not is_package_manager_busy(): apt_unhold_freedombox() subprocess.Popen(['systemctl', 'start', 'freedombox-manual-upgrade'], @@ -538,6 +538,11 @@ def subcommand_start_dist_upgrade(arguments): Check if a new stable release is available, and start dist-upgrade process if updates are enabled. """ + # In case freedombox package was left in held state by an + # interrupted process, release it. + if apt_hold_flag.exists() and not is_package_manager_busy(): + apt_unhold_freedombox() + upgrade_ready, reason = _check_dist_upgrade(arguments.test) if upgrade_ready: with open(DIST_UPGRADE_SERVICE_PATH, 'w') as service_file: diff --git a/plinth/action_utils.py b/plinth/action_utils.py index 85b5f057c..f206ed76d 100644 --- a/plinth/action_utils.py +++ b/plinth/action_utils.py @@ -460,3 +460,15 @@ def apt_unhold_freedombox(): subprocess.check_call(['apt-mark', 'unhold', 'freedombox']) if apt_hold_flag.exists(): apt_hold_flag.unlink() + + +def is_package_manager_busy(): + """Return whether package manager is busy. + This command uses the `lsof` command to check whether the dpkg lock file + is open which indicates that the package manager is busy""" + LOCK_FILE = '/var/lib/dpkg/lock' + try: + subprocess.check_output(['lsof', LOCK_FILE]) + return True + except subprocess.CalledProcessError: + return False