Skip to content

Commit

Permalink
Pass {USER, COREOS}_DATA separately in testcloud (#3266)
Browse files Browse the repository at this point in the history
Adjust the test for now to exercise the custom command path only.
Reboot timeout in testcloud's `instance.reboot()` will be handled
separately.

Co-authored-by: Petr Šplíchal <psplicha@redhat.com>
  • Loading branch information
frantisekz and psss authored Oct 21, 2024
1 parent abcff92 commit 7563006
Show file tree
Hide file tree
Showing 5 changed files with 22 additions and 12 deletions.
5 changes: 5 additions & 0 deletions docs/releases.rst
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,11 @@ discovered tests. This can be useful especially when fetching
tests from remote repositories where the user does not have write
access.

A race condition in the
:ref:`/plugins/provision/virtual.testcloud` plugin has been fixed,
thus multihost tests using this provision method should now work
reliably without unexpected connection failures.


tmt-1.37.0
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Expand Down
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ provision-beaker = [
"mrack>=1.15.1",
]
provision-virtual = [
"testcloud>=0.9.13",
"testcloud>=0.11.3",
]
provision-container = []
report-junit = [
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
summary: Reboot quickly
test: '[ "$TMT_REBOOT_COUNT" == "0" ] && tmt-reboot -t 1 || echo'
test: '[ "$TMT_REBOOT_COUNT" == "0" ] && tmt-reboot -t 1 -c reboot || echo'
framework: shell
2 changes: 1 addition & 1 deletion tmt.spec
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ Provides: tmt-provision-virtual == %{version}-%{release}
Obsoletes: tmt-provision-virtual < %{version}-%{release}
%endif
Requires: tmt == %{version}-%{release}
Requires: python3-testcloud >= 0.9.13
Requires: python3-testcloud >= 0.11.3
Requires: libvirt-daemon-config-network
Requires: openssh-clients
Requires: (ansible or ansible-core)
Expand Down
23 changes: 14 additions & 9 deletions tmt/steps/provision/testcloud.py
Original file line number Diff line number Diff line change
Expand Up @@ -740,12 +740,15 @@ def wake(self) -> None:
self._domain = DomainConfiguration(self.instance_name)
self._apply_hw_arch(self._domain, self.is_kvm, self.is_legacy_os)

# Is this a CoreOS?
self._domain.coreos = self.is_coreos

self._instance = testcloud.instance.Instance(
domain_configuration=self._domain,
image=self._image, desired_arch=self.arch,
connection=f"qemu:///{self.connection}")

def prepare_ssh_key(self, key_type: Optional[str] = None) -> None:
def prepare_ssh_key(self, key_type: Optional[str] = None) -> str:
""" Prepare ssh key for authentication """
assert self.workdir is not None

Expand All @@ -754,6 +757,7 @@ def prepare_ssh_key(self, key_type: Optional[str] = None) -> None:
self.debug("Extract public key from the provided private one.")
command = Command("ssh-keygen", "-f", self.key[0], "-y")
public_key = self._run_guest_command(command, silent=True).stdout
assert public_key is not None
# Generate new ssh key pair
else:
self.debug('Generating an ssh key.')
Expand All @@ -766,11 +770,7 @@ def prepare_ssh_key(self, key_type: Optional[str] = None) -> None:
self.verbose('key', self.key[0], 'green')
public_key = (self.workdir / f'{key_name}.pub').read_text()

# Place public key content into the machine configuration
self.config.USER_DATA = Template(USER_DATA).safe_substitute(
user_name=self.user, public_key=public_key)
self.config.COREOS_DATA = Template(COREOS_DATA).safe_substitute(
user_name=self.user, public_key=public_key)
return public_key

def prepare_config(self) -> None:
""" Prepare common configuration """
Expand Down Expand Up @@ -1008,18 +1008,23 @@ def start(self) -> None:

# Prepare ssh key
# TODO: Maybe... some better way to do this?
public_key = self.prepare_ssh_key(SSH_KEYGEN_TYPE)
if self._domain.coreos:
self._instance.coreos = True
# prepare_ssh_key() writes key directly to COREOS_DATA
self._instance.ssh_path = []
self.prepare_ssh_key(SSH_KEYGEN_TYPE)
data_tpl = Template(COREOS_DATA).safe_substitute(
user_name=self.user, public_key=public_key)
else:
data_tpl = Template(USER_DATA).safe_substitute(
user_name=self.user, public_key=public_key)

# Boot the virtual machine
self.info('progress', 'booting...', 'cyan')
assert libvirt is not None

try:
self._instance.prepare()
self._instance.prepare(data_tpl=data_tpl)
self._instance.spawn_vm()
self._instance.start(BOOT_TIMEOUT * time_coeff)
except (testcloud.exceptions.TestcloudInstanceError,
Expand Down Expand Up @@ -1077,7 +1082,7 @@ def reboot(self,
""" Reboot the guest, return True if successful """
# Use custom reboot command if provided
if command:
return super().reboot(hard=hard, command=command)
return super().reboot(hard=hard, command=command, timeout=timeout)
if not self._instance:
raise tmt.utils.ProvisionError("No instance initialized.")
self._instance.reboot(soft=not hard)
Expand Down

0 comments on commit 7563006

Please sign in to comment.