Revision 83e5e26f
b/lib/watcher/__init__.py | ||
---|---|---|
39 | 39 |
|
40 | 40 |
from ganeti import utils |
41 | 41 |
from ganeti import constants |
42 |
from ganeti import compat |
|
42 | 43 |
from ganeti import serializer |
43 | 44 |
from ganeti import errors |
44 | 45 |
from ganeti import opcodes |
... | ... | |
390 | 391 |
"""Abstraction for a Virtual Machine instance. |
391 | 392 |
|
392 | 393 |
""" |
393 |
def __init__(self, name, state, autostart): |
|
394 |
def __init__(self, name, state, autostart, snodes):
|
|
394 | 395 |
self.name = name |
395 | 396 |
self.state = state |
396 | 397 |
self.autostart = autostart |
398 |
self.snodes = snodes |
|
397 | 399 |
|
398 | 400 |
def Restart(self): |
399 | 401 |
"""Encapsulates the start of an instance. |
... | ... | |
445 | 447 |
smap[node] = [] |
446 | 448 |
smap[node].append(name) |
447 | 449 |
|
448 |
instances[name] = Instance(name, status, autostart) |
|
450 |
instances[name] = Instance(name, status, autostart, snodes)
|
|
449 | 451 |
|
450 | 452 |
nodes = dict([(name, (bootid, offline)) |
451 | 453 |
for name, bootid, offline in all_results[1]]) |
... | ... | |
575 | 577 |
notepad.RemoveInstance(instance) |
576 | 578 |
logging.info("Restart of %s succeeded", instance.name) |
577 | 579 |
|
578 |
@staticmethod |
|
579 |
def VerifyDisks(): |
|
580 |
def _CheckForOfflineNodes(self, instance): |
|
581 |
"""Checks if given instances has any secondary in offline status. |
|
582 |
|
|
583 |
@param instance: The instance object |
|
584 |
@return: True if any of the secondary is offline, False otherwise |
|
585 |
|
|
586 |
""" |
|
587 |
bootids = [] |
|
588 |
for node in instance.snodes: |
|
589 |
bootids.append(self.bootids[node]) |
|
590 |
|
|
591 |
return compat.any(offline for (_, offline) in bootids) |
|
592 |
|
|
593 |
def VerifyDisks(self): |
|
580 | 594 |
"""Run gnt-cluster verify-disks. |
581 | 595 |
|
582 | 596 |
""" |
... | ... | |
587 | 601 |
if not isinstance(result, (tuple, list)): |
588 | 602 |
logging.error("Can't get a valid result from verify-disks") |
589 | 603 |
return |
590 |
offline_disk_instances = result[2]
|
|
604 |
offline_disk_instances = result[1]
|
|
591 | 605 |
if not offline_disk_instances: |
592 | 606 |
# nothing to do |
593 | 607 |
return |
... | ... | |
595 | 609 |
utils.CommaJoin(offline_disk_instances)) |
596 | 610 |
# we submit only one job, and wait for it. not optimal, but spams |
597 | 611 |
# less the job queue |
598 |
job = [opcodes.OpInstanceActivateDisks(instance_name=name) |
|
599 |
for name in offline_disk_instances] |
|
600 |
job_id = cli.SendJob(job, cl=client) |
|
612 |
job = [] |
|
613 |
for name in offline_disk_instances: |
|
614 |
instance = self.instances[name] |
|
615 |
if (instance.state in HELPLESS_STATES or |
|
616 |
self._CheckForOfflineNodes(instance)): |
|
617 |
logging.info("Skip instance %s because it is in helpless state or has" |
|
618 |
" one offline secondary", name) |
|
619 |
continue |
|
620 |
job.append(opcodes.OpInstanceActivateDisks(instance_name=name)) |
|
601 | 621 |
|
602 |
try: |
|
603 |
cli.PollJob(job_id, cl=client, feedback_fn=logging.debug) |
|
604 |
except Exception: # pylint: disable-msg=W0703 |
|
605 |
logging.exception("Error while activating disks") |
|
622 |
if job: |
|
623 |
job_id = cli.SendJob(job, cl=client) |
|
624 |
|
|
625 |
try: |
|
626 |
cli.PollJob(job_id, cl=client, feedback_fn=logging.debug) |
|
627 |
except Exception: # pylint: disable-msg=W0703 |
|
628 |
logging.exception("Error while activating disks") |
|
606 | 629 |
|
607 | 630 |
|
608 | 631 |
def OpenStateFile(path): |
Also available in: Unified diff