1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147
|
summary: Check that preseeded ubuntu cloud image boots.
details: |
This test checks that preseeding of Ubuntu cloud images with snap-preseed
command works, and the resulting image boots and finalizes seeding.
The test assumes cloud image with a core and lxd snaps in its seeds/.
systems: [ubuntu-2*]
environment:
IMAGE_MOUNTPOINT: /mnt/cloudimg
prepare: |
#shellcheck source=tests/lib/preseed.sh
. "$TESTSLIB/preseed.sh"
# create a VM and mount a cloud image
tests.nested build-image classic
mkdir -p "$IMAGE_MOUNTPOINT"
IMAGE_NAME=$(tests.nested get image-name classic)
mount_ubuntu_image "$(tests.nested get images-path)/$IMAGE_NAME" "$IMAGE_MOUNTPOINT"
# on 20.04 snapd from the deb is newer than snapd from seeds;
# this is not a sensible scenario for preseeding but since
# we're cheating and preseeding images that were not meant to be
# preseeded in their current state, we need to inject newer snapd
# into seeds/ to make snap-preseed and the test happy.
# add snapd from this branch into the seed
# shellcheck source=tests/lib/prepare.sh
. "$TESTSLIB"/prepare.sh
build_snapd_snap .
mv snapd_*.snap snapd.snap
inject_snap_into_seed "$IMAGE_MOUNTPOINT" snapd
# test-postgres-system-usernames injected below uses core18 base, while the
# cloud image seed may already be shipping with core20 only
if [ "$(find "$IMAGE_MOUNTPOINT/var/lib/snapd/seed/snaps" -name 'core18*.snap' | wc -l)" = 0 ]; then
snap download --edge --basename=core18 core18
inject_snap_into_seed "$IMAGE_MOUNTPOINT" core18
rm core18.snap
fi
# inject a snap that uses system-usernames into the seed to confirm that works
# as expected
# TODO: replace this snap with a simpler one instead that is smaller, this one
# is 37M, but test-snapd-daemon-user does not have a daemon yet
snap download --edge --basename=test-postgres-system-usernames test-postgres-system-usernames
inject_snap_into_seed "$IMAGE_MOUNTPOINT" test-postgres-system-usernames
# for images that are already preseeded, we need to undo the preseeding there
echo "Running preseed --reset for already preseeded cloud images"
SNAPD_DEBUG=1 /usr/lib/snapd/snap-preseed --reset "$IMAGE_MOUNTPOINT"
restore: |
tests.nested vm remove
# any of the restore commands can fail depending on where execute part stopped,
# account for that with ||true.
#shellcheck source=tests/lib/preseed.sh
. "$TESTSLIB/preseed.sh"
umount_ubuntu_image "$IMAGE_MOUNTPOINT" || true
execute: |
#shellcheck source=tests/lib/preseed.sh
. "$TESTSLIB/preseed.sh"
echo "Running pre-seeding"
/usr/lib/snapd/snap-preseed "$IMAGE_MOUNTPOINT" | MATCH "using snapd binary: /tmp/snapd-preseed/usr/lib/snapd/snapd"
# mark-preseeded task is where snap-preseed stopped, therefore it's in Doing.
snap debug state "$IMAGE_MOUNTPOINT"/var/lib/snapd/state.json --change=1 | MATCH "Doing .+ mark-preseeded +Mark system pre-seeded"
snap debug state "$IMAGE_MOUNTPOINT"/var/lib/snapd/state.json | MATCH "Doing .+ Initialize system state"
cp "$IMAGE_MOUNTPOINT/var/lib/snapd/system-key" system-key.preseeded
#shellcheck source=tests/lib/preseed.sh
. "$TESTSLIB/preseed.sh"
umount_ubuntu_image "$IMAGE_MOUNTPOINT"
tests.nested create-vm classic
echo "Waiting for firstboot seeding to finish"
remote.exec "sudo snap wait system seed.loaded"
remote.exec "snap changes" | MATCH "Done .+ Initialize system state"
echo "Checking that the system-key after first boot is the same as that from preseeding"
# TODO: re-enable the system-key check when we are using the same kernel for
# the host VM as the nested VM, currently we are not, and as such there is a
# diff between the preseed apparmor-features and the nested VM actual
# system-key
if not os.query is-focal && not os.query is-jammy && not os.query is-noble; then
# note, this doesn't actually test the functionality, but acts as a canary:
# the test is run against a vm image with ubuntu release matching that from spread host;
# system-key check can fail if the nested vm image differs too much from the spread host system,
# e.g. when the list of apparmor features differs due to significant kernel update.
remote.exec "cat /var/lib/snapd/system-key" > system-key.real
diff -u -w system-key.real system-key.preseeded
# also check the system-key diff using snap debug seeding
# we should not have had any system-key difference as per above, so we
# shouldn't output the preseed system-key or the seed-restart-system-key
remote.exec "snap debug seeding" | NOMATCH "preseed-system-key:"
remote.exec "snap debug seeding" | NOMATCH "seed-restart-system-key:"
fi
remote.exec "snap debug seeding" | MATCH "preseeded:\s+true"
remote.exec "snap debug seeding" | MATCH "seeded:\s+true"
# FIXME: this just checks that the time is of the form "xxx.xxxs", which could
# break if the preseeding takes more than 60s and golang formats the
# time.Duration as "1m2.03s", etc. but for now this should be good enough
remote.exec "snap debug seeding" | MATCH "image-preseeding:\s+[0-9]+\.[0-9]+s"
remote.exec "snap debug seeding" | MATCH "seed-completion:\s+[0-9]+\.[0-9]+s"
# there is no longer any seeded snaps in base or minimal cloud images
# in noble, skip lxd checks for noble
if not os.query is-noble; then
echo "Checking that lxd snap is operational"
remote.exec "snap list" | NOMATCH "broken"
remote.exec "snap services" | MATCH "lxd.activate +enabled +inactive"
remote.exec "snap services" | MATCH "lxd.daemon +enabled +inactive +socket-activated"
remote.exec "sudo lxd init --auto"
remote.exec "snap services" | MATCH "+lxd.daemon +enabled +active +socket-activated"
fi
echo "Checking that the test-postgres-system-usernames snap is operational"
remote.exec "sudo snap start --enable test-postgres-system-usernames.postgres"
# wait for postgres to come online
sleep 10
remote.exec "snap services" | MATCH "+test-postgres-system-usernames.postgres +enabled +active"
echo "Checking that mark-seeded task was executed last"
# snap debug timings are sorts by read-time, mark-seeded should be last
remote.exec "sudo snap debug timings 1" | tail -2 | MATCH "Mark system seeded"
# no task should have ready time after mark-seeded
# shellcheck disable=SC2046
MARK_SEEDED_TIME=$(date -d $(snap change 1 --abs-time | grep "Mark system seeded" | awk '{print $3}') "+%s")
for RT in $(snap change 1 --abs-time | grep Done | awk '{print $3}' )
do
READY_TIME=$(date -d "$RT" "+%s")
if [ "$READY_TIME" -gt "$MARK_SEEDED_TIME" ]; then
echo "Unexpected ready time greater than mark-seeded ready"
snap change 1
fi
done
|