Skip to content

Commit

Permalink
Use 'xe' for VM migration instead of 'xo_cli'
Browse files Browse the repository at this point in the history
- Add param 'formated_args' to 'Host.xe' when needing to format
the params in the test code instead of in the 'xe' method
- Use it in the migration code for vdi/vif mapping

Signed-off-by: Benjamin Reis <[email protected]>
  • Loading branch information
benjamreis committed Jan 23, 2024
1 parent f367c80 commit 2f46236
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 22 deletions.
4 changes: 2 additions & 2 deletions lib/host.py
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ def scp(self, src, dest, check=True, suppress_fingerprint_warnings=True, local_d
suppress_fingerprint_warnings=suppress_fingerprint_warnings, local_dest=local_dest
)

def xe(self, action, args={}, check=True, simple_output=True, minimal=False, force=False):
def xe(self, action, args={}, formated_args=[], check=True, simple_output=True, minimal=False, force=False):
maybe_param_minimal = ['--minimal'] if minimal else []
maybe_param_force = ['--force'] if force else []

Expand All @@ -77,7 +77,7 @@ def stringify(key, value):
return "{}={}".format(key, shlex.quote(value))

command = ['xe', action] + maybe_param_minimal + maybe_param_force + \
[stringify(key, value) for key, value in args.items()]
[stringify(key, value) for key, value in args.items()] + formated_args
result = self.ssh(
command,
check=check,
Expand Down
53 changes: 33 additions & 20 deletions lib/vm.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
from lib.common import PackageManagerEnum, parse_xe_dict, safe_split, wait_for, wait_for_not
from lib.snapshot import Snapshot
from lib.vif import VIF
from lib.xo import xo_object_exists, xo_cli

class VM(BaseVM):
def __init__(self, uuid, host):
Expand Down Expand Up @@ -178,31 +177,45 @@ def exists(self):
def exists_on_previous_pool(self):
return self.previous_host.pool_has_vm(self.uuid)

def migrate(self, target_host, sr=None):
# workaround XO bug where sometimes it loses connection without knowing it
self.host.pool.master.xo_server_reconnect()
if target_host.pool != self.host.pool:
target_host.pool.master.xo_server_reconnect()

# Sometimes we migrate VMs right after creating them
# In that case we need to ensure that XO knows about the new VM
# Else we risk getting a "no such VM" error
# Thus, let's first wait for XO to know about the VM
wait_for(lambda: xo_object_exists(self.uuid), "Wait for XO to know about VM %s" % self.uuid)

def migrate(self, target_host, sr=None, network=None):
msg = "Migrate VM to host %s" % target_host
params = {
'vm': self.uuid,
'targetHost': target_host.uuid
'uuid': self.uuid,
'host-uuid': target_host.uuid,
'live': self.is_running()
}
cross_pool = self.host.pool.uuid != target_host.pool.uuid
if sr is not None:
msg += " (SR: %s)" % sr.uuid
mapping = {}
for vdi_uuid in self.vdi_uuids():
mapping[vdi_uuid] = sr.uuid
params['mapVdisSrs'] = 'json:' + json.dumps(mapping)
if network is not None:
msg += " (Network: %s)" % network
logging.info(msg)
xo_cli('vm.migrate', params)

storage_motion = cross_pool or sr is not None or network is not None
vif_map = []
vdi_map = []
if storage_motion:
remote_master = target_host.pool.master
params['remote-master'] = remote_master.hostname_or_ip
params['remote-username'] = remote_master.user
params['remote-password'] = remote_master.password

if sr is not None:
sr_uuid = sr.uuid
else:
sr_uuid = target_host.xe('pool-param-get', {'uuid': target_host.pool.uuid, 'param-name': 'default-SR'})
for vdi_uuid in self.vdi_uuids():
vdi_map += [f"vdi:{vdi_uuid}={sr_uuid}"]

if cross_pool:
# VIF Mapping
if network is None:
network = remote_master.management_network()
for vif in self.vifs():
vif_map += [f"vif:{vif.uuid}={network}"]

self.host.xe('vm-migrate', params, formated_args=vdi_map + vif_map)

self.previous_host = self.host
self.host = target_host

Expand Down

0 comments on commit 2f46236

Please sign in to comment.