mirror of
https://github.com/clearlinux/swupd-client.git
synced 2026-09-03 20:21:29 +00:00
Add --path to swupd autoupdate mechanism
Signed-off-by: Karthik Prabhu Vinod <karthik.prabhu.vinod@intel.com> Fixes #527
This commit is contained in:
committed by
Otavio Pontes
parent
1c499ccaa3
commit
c207c9240c
+3
-2
@@ -14,7 +14,7 @@ env:
|
||||
- UPDATE_SUBGROUP2_TOTAL="$((UPDATE_TOTAL - UPDATE_SUBGROUP1_TOTAL))"
|
||||
- UPDATE_SUBGROUP1="$(find test/functional/update -name *.bats | head -n $UPDATE_SUBGROUP1_TOTAL | tr '\n' ' ')"
|
||||
- UPDATE_SUBGROUP2="$(find test/functional/update -name *.bats | tail -n $UPDATE_SUBGROUP2_TOTAL | tr '\n' ' ')"
|
||||
- GROUP1="$UPDATE_SUBGROUP1 $(find test/functional/{bundleinfo,verify-legacy} -name *.bats -printf '%p ')"
|
||||
- GROUP1="$UPDATE_SUBGROUP1 $(find test/functional/{autoupdate,bundleinfo,verify-legacy} -name *.bats -printf '%p ')"
|
||||
- GROUP2="$UPDATE_SUBGROUP2 $(find test/functional/{checkupdate,hashdump,mirror,usability} -name *.bats \( ! -name usa-config-file.bats \) -printf '%p ')"
|
||||
- GROUP3="$(find test/functional/{diagnose,search,os-install,repair} -name *.bats -printf '%p ')"
|
||||
- GROUP4="$(find test/functional/{bundleadd,bundleremove,bundlelist,signature} -name *.bats -printf '%p ')"
|
||||
@@ -27,7 +27,7 @@ jobs:
|
||||
name: "Static Analysis & Unit Tests"
|
||||
script: make compliant && make shellcheck && sudo sh -c 'umask 0022 && make unit-check' && make docs-coverage
|
||||
- stage: test
|
||||
name: "Functional Tests - update (group 1), bundle-info, verify-legacy"
|
||||
name: "Functional Tests - update (group 1), autoupdate, bundle-info, verify-legacy"
|
||||
script: env TESTS="$GROUP1" make -e check
|
||||
- stage: test
|
||||
name: "Functional Tests - update (group 2), checkupdate, hashdump, mirror, usability"
|
||||
@@ -50,6 +50,7 @@ install:
|
||||
- sudo apt-get install doxygen
|
||||
- sudo apt-get install check
|
||||
- sudo pip install coverxygen
|
||||
- sudo ln -s /bin/systemctl /usr/bin/systemctl
|
||||
|
||||
# build bsdiff
|
||||
- wget https://github.com/clearlinux/bsdiff/releases/download/v1.0.2/bsdiff-1.0.2.tar.xz
|
||||
|
||||
+1
-1
@@ -165,6 +165,7 @@ BATS_LOG_DRIVER = $(tap_driver)
|
||||
TESTS = $(dist_check_SCRIPTS) $(UNIT_TESTS)
|
||||
|
||||
BATS = \
|
||||
test/functional/autoupdate/aup-basic.bats \
|
||||
test/functional/bundleadd/add-alias-basic.bats \
|
||||
test/functional/bundleadd/add-also-add-flag.bats \
|
||||
test/functional/bundleadd/add-bad-hash.bats \
|
||||
@@ -341,7 +342,6 @@ BATS = \
|
||||
test/functional/verify-legacy/verify-bundle.bats \
|
||||
test/functional/verify-legacy/verify-flags.bats
|
||||
|
||||
|
||||
UNIT_TESTS = \
|
||||
test/unit/test_list.test \
|
||||
test/unit/test_manifest.test \
|
||||
|
||||
+76
-41
@@ -29,56 +29,74 @@
|
||||
|
||||
#include "swupd.h"
|
||||
|
||||
static void print_help(const char *name)
|
||||
static void print_help(void)
|
||||
{
|
||||
print("Usage:\n");
|
||||
print(" swupd %s [options]\n\n", basename((char *)name));
|
||||
print("Help Options:\n");
|
||||
print(" -h, --help Show help options\n");
|
||||
print(" swupd autoupdate [OPTION...]\n\n");
|
||||
|
||||
global_print_help();
|
||||
|
||||
print("Options:\n");
|
||||
print(" --enable enable autoupdates\n");
|
||||
print(" --disable disable autoupdates\n");
|
||||
print("\n");
|
||||
}
|
||||
|
||||
static int enable;
|
||||
static int disable;
|
||||
#define FLAG_ENABLE 2000
|
||||
#define FLAG_DISABLE 2001
|
||||
static bool cmdline_option_enable;
|
||||
static bool cmdline_option_disable;
|
||||
|
||||
static const struct option prog_opts[] = {
|
||||
{ "help", no_argument, 0, 'h' },
|
||||
{ "enable", no_argument, &enable, 1 },
|
||||
{ "disable", no_argument, &disable, 1 },
|
||||
{ 0, 0, 0, 0 }
|
||||
{ "enable", no_argument, 0, FLAG_ENABLE },
|
||||
{ "disable", no_argument, 0, FLAG_DISABLE },
|
||||
};
|
||||
|
||||
static bool parse_opt(int opt, UNUSED_PARAM char *optarg)
|
||||
{
|
||||
switch (opt) {
|
||||
case 'h':
|
||||
print_help();
|
||||
exit(EXIT_SUCCESS);
|
||||
case FLAG_ENABLE:
|
||||
cmdline_option_enable = optarg_to_bool(optarg);
|
||||
return true;
|
||||
case FLAG_DISABLE:
|
||||
cmdline_option_disable = optarg_to_bool(optarg);
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static const struct global_options opts = {
|
||||
prog_opts,
|
||||
sizeof(prog_opts) / sizeof(struct option),
|
||||
parse_opt,
|
||||
print_help,
|
||||
};
|
||||
|
||||
static bool parse_options(int argc, char **argv)
|
||||
{
|
||||
int opt;
|
||||
int ind = global_parse_options(argc, argv, &opts);
|
||||
|
||||
while ((opt = getopt_long(argc, argv, "h", prog_opts, NULL)) != -1) {
|
||||
switch (opt) {
|
||||
case '?':
|
||||
print_help(argv[0]);
|
||||
exit(SWUPD_INVALID_OPTION);
|
||||
case 'h':
|
||||
print_help(argv[0]);
|
||||
exit(EXIT_SUCCESS);
|
||||
case 0: /* getopt_long has set the flag */
|
||||
break;
|
||||
default:
|
||||
error("unrecognized option\n\n");
|
||||
goto err;
|
||||
}
|
||||
if (ind < 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (argc > optind) {
|
||||
if (argc > ind) {
|
||||
error("unexpected arguments\n\n");
|
||||
goto err;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (cmdline_option_enable && cmdline_option_disable) {
|
||||
error("Can not use --enable and --disable options at the same time\n\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
err:
|
||||
print_help(argv[0]);
|
||||
return false;
|
||||
}
|
||||
|
||||
static void policy_warn(void)
|
||||
@@ -89,38 +107,50 @@ static void policy_warn(void)
|
||||
|
||||
enum swupd_code autoupdate_main(int argc, char **argv)
|
||||
{
|
||||
|
||||
if (!parse_options(argc, argv)) {
|
||||
print_help();
|
||||
return SWUPD_INVALID_OPTION;
|
||||
}
|
||||
if (enable && disable) {
|
||||
error("Can not enable and disable at the same time\n");
|
||||
return SWUPD_INVALID_OPTION;
|
||||
}
|
||||
if (!systemctl_active()) {
|
||||
|
||||
if (!globals.path_prefix && !systemctl_active()) {
|
||||
error("Systemd is inactive - unable to proceed\n");
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
}
|
||||
|
||||
if (enable) {
|
||||
if (cmdline_option_enable) {
|
||||
int rc;
|
||||
check_root();
|
||||
info("Running systemctl to enable updates\n");
|
||||
rc = systemctl_cmd("unmask", "--now", "swupd-update.service", "swupd-update.timer", NULL);
|
||||
rc = systemctl_cmd_path(globals.path_prefix,
|
||||
"unmask", "--now", "swupd-update.service", "swupd-update.timer", NULL);
|
||||
if (rc != 0) {
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
}
|
||||
rc = systemctl_restart("swupd-update.timer");
|
||||
|
||||
/* If globals.path_prefix is given and we have succeeded so far,
|
||||
* make sense to return SWUPD_OK at this point. In that case,
|
||||
* a swupd timer restart cannot be done as there is no
|
||||
* system daemon to communicate for rootfs.
|
||||
*/
|
||||
if (globals.path_prefix) {
|
||||
warn("Running autoupdate with --path will not restart swupd-update.timer. This will have to be done manually\n");
|
||||
return SWUPD_OK;
|
||||
}
|
||||
|
||||
rc = systemctl_cmd_path(globals.path_prefix, "restart", "swupd-update.timer", NULL);
|
||||
if (rc != 0) {
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
}
|
||||
|
||||
return SWUPD_OK;
|
||||
} else if (disable) {
|
||||
} else if (cmdline_option_disable) {
|
||||
int rc;
|
||||
check_root();
|
||||
policy_warn();
|
||||
info("Running systemctl to disable updates\n");
|
||||
rc = systemctl_cmd("mask", "--now", "swupd-update.service", "swupd-update.timer", NULL);
|
||||
rc = systemctl_cmd_path(globals.path_prefix,
|
||||
"mask", "--now", "swupd-update.service", "swupd-update.timer", NULL);
|
||||
if (rc) {
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
}
|
||||
@@ -128,8 +158,8 @@ enum swupd_code autoupdate_main(int argc, char **argv)
|
||||
} else {
|
||||
int rc1, rc2;
|
||||
const int STATUS_UNKNOWN = 4;
|
||||
rc1 = systemctl_cmd("is-enabled", "swupd-update.service", NULL);
|
||||
rc2 = systemctl_cmd("is-active", "swupd-update.timer", NULL);
|
||||
rc1 = systemctl_cmd_path(globals.path_prefix, "is-enabled", "swupd-update.service", NULL);
|
||||
rc2 = systemctl_cmd_path(globals.path_prefix, "is-active", "swupd-update.timer", NULL);
|
||||
if (rc1 == SWUPD_OK && rc2 == SWUPD_OK) {
|
||||
print("Enabled\n");
|
||||
return SWUPD_OK;
|
||||
@@ -137,6 +167,11 @@ enum swupd_code autoupdate_main(int argc, char **argv)
|
||||
/* systemctl returns 1,2, or 3 when program dead or not running */
|
||||
error("Unable to determine autoupdate status\n");
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
// Swupd-service is unmasked, static but timer is inactive for --path
|
||||
} else if (rc1 == SWUPD_OK && rc2 != SWUPD_OK && globals.path_prefix) {
|
||||
info("Autoupdate is enabled, but the timer is not running\n");
|
||||
error("Unable to determine autoupdate status with --path option\n");
|
||||
return SWUPD_SUBPROCESS_ERROR;
|
||||
} else {
|
||||
print("Disabled\n");
|
||||
return SWUPD_NO;
|
||||
|
||||
@@ -203,6 +203,12 @@ int sys_rm(const char *filename);
|
||||
*/
|
||||
#define systemctl_cmd(...) run_command_quiet(SYSTEMCTL, __VA_ARGS__)
|
||||
|
||||
/**
|
||||
* @brief Run a systemctl command with the informed parameters in a path
|
||||
*/
|
||||
#define systemctl_cmd_path(path, ...) \
|
||||
path ? run_command_quiet(SYSTEMCTL, "--root", path, __VA_ARGS__) : run_command_quiet(SYSTEMCTL, __VA_ARGS__)
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
+1
-1
@@ -34,7 +34,7 @@ _swupd()
|
||||
opts="$global "
|
||||
break;;
|
||||
("autoupdate")
|
||||
opts="--help --enable --disable "
|
||||
opts="$global --help --enable --disable "
|
||||
break;;
|
||||
("check-update")
|
||||
opts="$global "
|
||||
|
||||
@@ -185,6 +185,7 @@ if [[ -n "$state" ]]; then
|
||||
;;
|
||||
autoupdate)
|
||||
local -a autoupdates; autoupdates=(
|
||||
$global_opts
|
||||
'(-)--enable[enable autoupdates]'
|
||||
'(-)--disable[disable autoupdates]'
|
||||
'(-)'{-h,--help}'[Show help options]'
|
||||
|
||||
@@ -125,6 +125,7 @@ or more of the [assertions](#assertions) provided by the test library.
|
||||
|
||||
| Main Business Scenarios | Commands | Group ID |
|
||||
| ---------------------------------------------- | ------------- | -------- |
|
||||
| Enables/Disables autoupdate | auto-update | AUT |
|
||||
| Install new bundles | bundle-add | ADD |
|
||||
| Uninstall bundles | bundle-remove | REM |
|
||||
| List bundles | bundle-list | LST |
|
||||
|
||||
Executable
+63
@@ -0,0 +1,63 @@
|
||||
#!/usr/bin/env bats
|
||||
|
||||
# Author: Karthik Prabhu Vinod
|
||||
# Email: karthik.prabhu.vinod@intel.com
|
||||
|
||||
load "../testlib"
|
||||
|
||||
test_setup() {
|
||||
|
||||
if [ -z "$TRAVIS" ]; then
|
||||
skip "This test is intended to run only in Travis (use TRAVIS=true to run it anyway)..."
|
||||
fi
|
||||
|
||||
create_test_environment "$TEST_NAME"
|
||||
|
||||
}
|
||||
|
||||
test_teardown() {
|
||||
|
||||
if [ -z "$TRAVIS" ]; then
|
||||
return
|
||||
fi
|
||||
|
||||
destroy_test_environment "$TEST_NAME"
|
||||
|
||||
}
|
||||
|
||||
@test "AUT001: Basic test, Check auto-update enable" {
|
||||
|
||||
# perform autoupdate disable
|
||||
run sudo sh -c "$SWUPD autoupdate --disable --path=$PATH_PREFIX"
|
||||
assert_status_is "$SWUPD_OK"
|
||||
expected_output=$(cat <<-EOM
|
||||
Warning: disabling automatic updates may take you out of compliance with your IT policy
|
||||
Running systemctl to disable updates
|
||||
EOM
|
||||
)
|
||||
assert_is_output "$expected_output"
|
||||
|
||||
# check for files(should exist and point to /dev/null)
|
||||
run sudo sh -c "test -c $PATH_PREFIX/etc/systemd/system/swupd-update.service"
|
||||
assert_status_is "$SWUPD_OK"
|
||||
run sudo sh -c "test -c $PATH_PREFIX/etc/systemd/system/swupd-update.timer"
|
||||
assert_status_is "$SWUPD_OK"
|
||||
|
||||
# perform autoupdate enable
|
||||
run sudo sh -c "$SWUPD autoupdate --enable $SWUPD_OPTS"
|
||||
|
||||
assert_status_is "$SWUPD_OK"
|
||||
expected_output=$(cat <<-EOM
|
||||
Running systemctl to enable updates
|
||||
Warning: Running autoupdate with --path will not restart swupd-update.timer. This will have to be done manually
|
||||
EOM
|
||||
)
|
||||
assert_is_output "$expected_output"
|
||||
|
||||
# check for files(should not exist)
|
||||
run sudo sh -c "test -c $PATH_PREFIX/etc/systemd/system/swupd-update.service"
|
||||
assert_status_is_not "$SWUPD_OK"
|
||||
run sudo sh -c "test -c $PATH_PREFIX/etc/systemd/system/swupd-update.timer"
|
||||
assert_status_is_not "$SWUPD_OK"
|
||||
|
||||
}
|
||||
@@ -5,7 +5,7 @@ FUNC_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
# shellcheck source=/dev/null
|
||||
source "$FUNC_DIR"/testlib.bash
|
||||
|
||||
declare -A groups=( ["bundleadd"]="ADD" ["bundlelist"]="LST" ["bundleremove"]="REM" \
|
||||
declare -A groups=( ["autoupdate"]="AUT" ["bundleadd"]="ADD" ["bundlelist"]="LST" ["bundleremove"]="REM" \
|
||||
["checkupdate"]="CHK" ["hashdump"]="HSD" ["mirror"]="MIR" ["search"]="SRH" \
|
||||
["update"]="UPD" ["usability"]="USA" ["verify"]="VER" )
|
||||
|
||||
|
||||
@@ -3171,6 +3171,7 @@ get_next_available_id() { # swupd_function
|
||||
id=$((id+1))
|
||||
test_dir=$(basename "$(realpath "$test_dir")")
|
||||
case "$test_dir" in
|
||||
autoupdate) group=AUT;;
|
||||
bundleadd) group=ADD;;
|
||||
bundleremove) group=REM;;
|
||||
bundlelist) group=LST;;
|
||||
@@ -3184,7 +3185,6 @@ get_next_available_id() { # swupd_function
|
||||
completion) group=USA;;
|
||||
usability) group=USA;;
|
||||
signature) group=SIG;;
|
||||
autoupdate) group=AUT;;
|
||||
info) group=INF;;
|
||||
clean) group=CLN;;
|
||||
os-install) group=INS;;
|
||||
|
||||
Reference in New Issue
Block a user