Skip to content

Commit

Permalink
test: Wait until Disks table initialization before disk actions
Browse files Browse the repository at this point in the history
The disk kebabs keep jumping around while the Disk table initializes
and re-renders, which is a race condition when trying to click on them
with the actual browser mouse.

So robustify the tests to wait for the table to be complete. This
mitigates the issue, and also provides some nice extra validation. This
was already done in a few places, generalize this into a `waitDisks()`
helper.

Unfortunately in some cases waiting for the entries is still not enough,
but I can't figure out what else to wait on.. Do an extra sleep for the
table to settle down.
  • Loading branch information
martinpitt committed Aug 23, 2024
1 parent d6dc923 commit a69ae8e
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 7 deletions.
20 changes: 13 additions & 7 deletions test/check-machines-disks
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
b.wait_in_text("#vm-subVmTest1-system-state", "Running")

self.goToVmPage("subVmTest1")
self.waitDisks(["vda", "vde", "vdf", "vdg"])

# Test non-persistent disks are not configurable
b.wait_not_present("#vm-subVmTest1-disks-vdf-edit")
Expand Down Expand Up @@ -182,6 +183,8 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
m.execute(f"virsh attach-disk --domain subVmTest1 --source {p1}/mydisk4 --target sdb --targetbus sata --persistent")
b.reload()
b.enter_page('/machines')
# expected devices after bus type change
self.waitDisks(["sda", "sdb", "vda", "vdg"])
openDialog("sdb")
b.set_checked("#vm-subVmTest1-disks-sdb-edit-readonly", True)
save("sdb", xfail="readonly sata disks are not supported")
Expand All @@ -196,6 +199,9 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
# virsh attach-disk want send an event for offline VM changes
b.reload()
b.enter_page('/machines')
# expected devices after bus type change
self.waitDisks(["hda", "sdb", "vda", "vdg"])

openDialog("hda")
b._wait_present("#vm-subVmTest1-disks-hda-edit-bus-type option[value=sata]")
self.assertFalse(b.is_present("#vm-subVmTest1-disks-hda-edit-bus-type option[value=virtio]"))
Expand Down Expand Up @@ -224,6 +230,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
self.goToMainPage()
self.createVm("subVmTest2", running=False, os="unknown")
self.goToVmPage("subVmTest2")
self.waitDisks(["hda"], vm="subVmTest2")

b.wait_in_text("#vm-subVmTest2-disks-hda-bus", "ide")

Expand Down Expand Up @@ -296,7 +303,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
print("Restarting vm-subVmTest1, might take a while")
self.performAction("subVmTest1", "forceReboot")

b.wait_visible("#vm-subVmTest1-disks-vda-device")
self.waitDisks(["vda"])
b.wait_not_present("#vm-subVmTest1-disks-vdc-device")

# Check when no storage pool and adding existed disk
Expand Down Expand Up @@ -1046,8 +1053,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
release_target(used_targets, target)

permanent_targets = [t for t in used_targets if t not in transient_targets]
for target in permanent_targets:
b.wait_visible(f"#vm-subVmTest1-disks-{target}-device")
self.waitDisks(permanent_targets)

# Check that creating a new volume in default_tmp does not by
# accident use the defaults from defaultVol.iso. Those
Expand Down Expand Up @@ -1515,6 +1521,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
# Test detaching non permanent disk of a running domain
b.wait_in_text("#vm-subVmTest1-system-state", "Running")
self.goToVmPage("subVmTest1")
self.waitDisks(["vda", "vdc", "vdd", "vde"])

self.deleteDisk("vdc", expect_path=vdc_path)
# Wait for underlying VM's OS to detach the disk
Expand Down Expand Up @@ -1553,10 +1560,7 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):
b.reload()
b.enter_page('/machines')
self.waitPageInit()
b.wait_visible("#vm-subVmTest1-disks-sda-device")
b.wait_visible("#vm-subVmTest1-disks-sdb-device")
b.wait_visible("#vm-subVmTest1-disks-sdc-device")
b.wait_visible("#vm-subVmTest1-disks-vda-device")
self.waitDisks(["sda", "sdb", "sdc", "vda"])

def removeDiskAndChecks(target, path, removeFile=False, removeFileFail=False, removeFileNotPresent=False):
self.dropdownAction(f"#vm-subVmTest1-disks-{target}-action-kebab",
Expand Down Expand Up @@ -1651,6 +1655,8 @@ class TestMachinesDisks(machineslib.VirtualMachinesCase):

b.wait_in_text("#vm-subVmTest1-system-state", "Running")
self.goToVmPage("subVmTest1")
# wait until Disks have initialized; otherwise the kebabs jump around
self.waitDisks(["sda", "vda"])

self.VMInsertMediaDialog(
self,
Expand Down
2 changes: 2 additions & 0 deletions test/check-machines-storage-pools
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,8 @@ class TestMachinesStoragePools(machineslib.VirtualMachinesCase):
self.goToMainPage()
self.waitVmRow("subVmTest1")
self.goToVmPage("subVmTest1")
self.waitDisks(["vda", "vdc"])

self.deleteDisk("vdc")
self.goToMainPage()
b.click(".pf-v5-c-card .pf-v5-c-card__header button:contains(Storage pools)")
Expand Down
11 changes: 11 additions & 0 deletions test/machineslib.py
Original file line number Diff line number Diff line change
Expand Up @@ -343,6 +343,17 @@ def waitLogFile(self, logfile, expected_text):
def waitGuestBooted(self, logfile):
self.waitLogFile(logfile, "Welcome to Alpine Linux")

def waitDisks(self, expected_disks: list[str], vm="subVmTest1"):
"""Wait until Disks table initialized on the details
This prevents the kebabs from jumping around during re-renders, which
makes trying to click on them racy.
"""
for disk in expected_disks:
self.browser.wait_visible(f"#vm-{vm}-disks-{disk}-device") # type: ignore[attr-defined]
# HACK: we need to wait on *something* else, but no idea what..
time.sleep(0.5)


class VirtualMachinesCase(testlib.MachineCase, VirtualMachinesCaseHelpers, storagelib.StorageHelpers, netlib.NetworkHelpers):
def setUp(self):
Expand Down

0 comments on commit a69ae8e

Please sign in to comment.