Revision b44bd844
b/lib/cli.py | ||
---|---|---|
83 | 83 |
"IDENTIFY_DEFAULTS_OPT", |
84 | 84 |
"IGNORE_CONSIST_OPT", |
85 | 85 |
"IGNORE_FAILURES_OPT", |
86 |
"IGNORE_OFFLINE_OPT", |
|
86 | 87 |
"IGNORE_REMOVE_FAILURES_OPT", |
87 | 88 |
"IGNORE_SECONDARIES_OPT", |
88 | 89 |
"IGNORE_SIZE_OPT", |
... | ... | |
585 | 586 |
CONFIRM_OPT = cli_option("--yes", dest="confirm", action="store_true", |
586 | 587 |
default=False, help="Do not require confirmation") |
587 | 588 |
|
589 |
IGNORE_OFFLINE_OPT = cli_option("--ignore-offline", dest="ignore_offline", |
|
590 |
action="store_true", default=False, |
|
591 |
help=("Ignore offline nodes and do as much" |
|
592 |
" as possible")) |
|
593 |
|
|
588 | 594 |
TAG_SRC_OPT = cli_option("--from", dest="tags_source", |
589 | 595 |
default=None, help="File with tag names") |
590 | 596 |
|
b/lib/cmdlib.py | ||
---|---|---|
73 | 73 |
#: a required instance name (for single-instance LUs) |
74 | 74 |
_PInstanceName = ("instance_name", ht.NoDefault, ht.TNonEmptyString) |
75 | 75 |
|
76 |
#: Whether to ignore offline nodes |
|
77 |
_PIgnoreOfflineNodes = ("ignore_offline_nodes", False, ht.TBool) |
|
76 | 78 |
|
77 | 79 |
#: a required node name (for single-node LUs) |
78 | 80 |
_PNodeName = ("node_name", ht.NoDefault, ht.TNonEmptyString) |
... | ... | |
4413 | 4415 |
_OP_PARAMS = [ |
4414 | 4416 |
_PInstanceName, |
4415 | 4417 |
_PForce, |
4418 |
_PIgnoreOfflineNodes, |
|
4416 | 4419 |
("hvparams", ht.EmptyDict, ht.TDict), |
4417 | 4420 |
("beparams", ht.EmptyDict, ht.TDict), |
4418 | 4421 |
] |
... | ... | |
4461 | 4464 |
hv_type.CheckParameterSyntax(filled_hvp) |
4462 | 4465 |
_CheckHVParams(self, instance.all_nodes, instance.hypervisor, filled_hvp) |
4463 | 4466 |
|
4464 |
_CheckNodeOnline(self, instance.primary_node)
|
|
4467 |
self.primary_offline = self.cfg.GetNodeInfo(instance.primary_node).offline
|
|
4465 | 4468 |
|
4466 |
bep = self.cfg.GetClusterInfo().FillBE(instance) |
|
4467 |
# check bridges existence |
|
4468 |
_CheckInstanceBridgesExist(self, instance) |
|
4469 |
if self.primary_offline and self.op.ignore_offline_nodes: |
|
4470 |
self.proc.LogWarning("Ignoring offline primary node") |
|
4471 |
|
|
4472 |
if self.op.hvparams or self.op.beparams: |
|
4473 |
self.proc.LogWarning("Overridden parameters are ignored") |
|
4474 |
else: |
|
4475 |
_CheckNodeOnline(self, instance.primary_node) |
|
4476 |
|
|
4477 |
bep = self.cfg.GetClusterInfo().FillBE(instance) |
|
4469 | 4478 |
|
4470 |
remote_info = self.rpc.call_instance_info(instance.primary_node, |
|
4471 |
instance.name, |
|
4472 |
instance.hypervisor) |
|
4473 |
remote_info.Raise("Error checking node %s" % instance.primary_node, |
|
4474 |
prereq=True, ecode=errors.ECODE_ENVIRON) |
|
4475 |
if not remote_info.payload: # not running already |
|
4476 |
_CheckNodeFreeMemory(self, instance.primary_node, |
|
4477 |
"starting instance %s" % instance.name, |
|
4478 |
bep[constants.BE_MEMORY], instance.hypervisor) |
|
4479 |
# check bridges existence |
|
4480 |
_CheckInstanceBridgesExist(self, instance) |
|
4481 |
|
|
4482 |
remote_info = self.rpc.call_instance_info(instance.primary_node, |
|
4483 |
instance.name, |
|
4484 |
instance.hypervisor) |
|
4485 |
remote_info.Raise("Error checking node %s" % instance.primary_node, |
|
4486 |
prereq=True, ecode=errors.ECODE_ENVIRON) |
|
4487 |
if not remote_info.payload: # not running already |
|
4488 |
_CheckNodeFreeMemory(self, instance.primary_node, |
|
4489 |
"starting instance %s" % instance.name, |
|
4490 |
bep[constants.BE_MEMORY], instance.hypervisor) |
|
4479 | 4491 |
|
4480 | 4492 |
def Exec(self, feedback_fn): |
4481 | 4493 |
"""Start the instance. |
... | ... | |
4486 | 4498 |
|
4487 | 4499 |
self.cfg.MarkInstanceUp(instance.name) |
4488 | 4500 |
|
4489 |
node_current = instance.primary_node |
|
4501 |
if self.primary_offline: |
|
4502 |
assert self.op.ignore_offline_nodes |
|
4503 |
self.proc.LogInfo("Primary node offline, marked instance as started") |
|
4504 |
else: |
|
4505 |
node_current = instance.primary_node |
|
4490 | 4506 |
|
4491 |
_StartInstanceDisks(self, instance, force) |
|
4507 |
_StartInstanceDisks(self, instance, force)
|
|
4492 | 4508 |
|
4493 |
result = self.rpc.call_instance_start(node_current, instance, |
|
4494 |
self.op.hvparams, self.op.beparams) |
|
4495 |
msg = result.fail_msg |
|
4496 |
if msg: |
|
4497 |
_ShutdownInstanceDisks(self, instance) |
|
4498 |
raise errors.OpExecError("Could not start instance: %s" % msg) |
|
4509 |
result = self.rpc.call_instance_start(node_current, instance,
|
|
4510 |
self.op.hvparams, self.op.beparams)
|
|
4511 |
msg = result.fail_msg
|
|
4512 |
if msg:
|
|
4513 |
_ShutdownInstanceDisks(self, instance)
|
|
4514 |
raise errors.OpExecError("Could not start instance: %s" % msg)
|
|
4499 | 4515 |
|
4500 | 4516 |
|
4501 | 4517 |
class LURebootInstance(LogicalUnit): |
... | ... | |
4587 | 4603 |
HTYPE = constants.HTYPE_INSTANCE |
4588 | 4604 |
_OP_PARAMS = [ |
4589 | 4605 |
_PInstanceName, |
4606 |
_PIgnoreOfflineNodes, |
|
4590 | 4607 |
("timeout", constants.DEFAULT_SHUTDOWN_TIMEOUT, ht.TPositiveInt), |
4591 | 4608 |
] |
4592 | 4609 |
REQ_BGL = False |
... | ... | |
4614 | 4631 |
self.instance = self.cfg.GetInstanceInfo(self.op.instance_name) |
4615 | 4632 |
assert self.instance is not None, \ |
4616 | 4633 |
"Cannot retrieve locked instance %s" % self.op.instance_name |
4617 |
_CheckNodeOnline(self, self.instance.primary_node) |
|
4634 |
|
|
4635 |
self.primary_offline = \ |
|
4636 |
self.cfg.GetNodeInfo(self.instance.primary_node).offline |
|
4637 |
|
|
4638 |
if self.primary_offline and self.op.ignore_offline_nodes: |
|
4639 |
self.proc.LogWarning("Ignoring offline primary node") |
|
4640 |
else: |
|
4641 |
_CheckNodeOnline(self, self.instance.primary_node) |
|
4618 | 4642 |
|
4619 | 4643 |
def Exec(self, feedback_fn): |
4620 | 4644 |
"""Shutdown the instance. |
... | ... | |
4623 | 4647 |
instance = self.instance |
4624 | 4648 |
node_current = instance.primary_node |
4625 | 4649 |
timeout = self.op.timeout |
4650 |
|
|
4626 | 4651 |
self.cfg.MarkInstanceDown(instance.name) |
4627 |
result = self.rpc.call_instance_shutdown(node_current, instance, timeout) |
|
4628 |
msg = result.fail_msg |
|
4629 |
if msg: |
|
4630 |
self.proc.LogWarning("Could not shutdown instance: %s" % msg) |
|
4631 | 4652 |
|
4632 |
_ShutdownInstanceDisks(self, instance) |
|
4653 |
if self.primary_offline: |
|
4654 |
assert self.op.ignore_offline_nodes |
|
4655 |
self.proc.LogInfo("Primary node offline, marked instance as stopped") |
|
4656 |
else: |
|
4657 |
result = self.rpc.call_instance_shutdown(node_current, instance, timeout) |
|
4658 |
msg = result.fail_msg |
|
4659 |
if msg: |
|
4660 |
self.proc.LogWarning("Could not shutdown instance: %s" % msg) |
|
4661 |
|
|
4662 |
_ShutdownInstanceDisks(self, instance) |
|
4633 | 4663 |
|
4634 | 4664 |
|
4635 | 4665 |
class LUReinstallInstance(LogicalUnit): |
b/lib/opcodes.py | ||
---|---|---|
519 | 519 |
OP_ID = "OP_INSTANCE_STARTUP" |
520 | 520 |
OP_DSC_FIELD = "instance_name" |
521 | 521 |
__slots__ = [ |
522 |
"instance_name", "force", "hvparams", "beparams", |
|
522 |
"instance_name", "force", "hvparams", "beparams", "ignore_offline_nodes",
|
|
523 | 523 |
] |
524 | 524 |
|
525 | 525 |
|
... | ... | |
527 | 527 |
"""Shutdown an instance.""" |
528 | 528 |
OP_ID = "OP_INSTANCE_SHUTDOWN" |
529 | 529 |
OP_DSC_FIELD = "instance_name" |
530 |
__slots__ = ["instance_name", "timeout"] |
|
530 |
__slots__ = [ |
|
531 |
"instance_name", "timeout", "ignore_offline_nodes", |
|
532 |
] |
|
531 | 533 |
|
532 | 534 |
|
533 | 535 |
class OpRebootInstance(OpCode): |
b/man/gnt-instance.sgml | ||
---|---|---|
1741 | 1741 |
<command>startup</command> |
1742 | 1742 |
<sbr> |
1743 | 1743 |
<arg>--force</arg> |
1744 |
<arg>--ignore-offline</arg> |
|
1744 | 1745 |
<sbr> |
1745 | 1746 |
<arg>--force-multiple</arg> |
1746 | 1747 |
<sbr> |
... | ... | |
1848 | 1849 |
|
1849 | 1850 |
<para> |
1850 | 1851 |
Use <option>--force</option> to start even if secondary disks are |
1851 |
failing. |
|
1852 |
failing. <option>--ignore-offline</option> can be used to ignore |
|
1853 |
offline primary nodes and mark the instance as started even if |
|
1854 |
the primary is not available. |
|
1852 | 1855 |
</para> |
1853 | 1856 |
|
1854 | 1857 |
<para> |
... | ... | |
1904 | 1907 |
<arg>--timeout=<replaceable>N</replaceable></arg> |
1905 | 1908 |
<sbr> |
1906 | 1909 |
<arg>--force-multiple</arg> |
1910 |
<arg>--ignore-offline</arg> |
|
1907 | 1911 |
<sbr> |
1908 | 1912 |
<group choice="opt"> |
1909 | 1913 |
<arg>--instance</arg> |
... | ... | |
1954 | 1958 |
<command>gnt-job info</command>. |
1955 | 1959 |
</para> |
1956 | 1960 |
|
1961 |
<para> |
|
1962 |
<option>--ignore-offline</option> can be used to ignore offline |
|
1963 |
primary nodes and force the instance to be marked as stopped. This |
|
1964 |
option should be used with care as it can lead to an |
|
1965 |
inconsistent cluster state. |
|
1966 |
</para> |
|
1957 | 1967 |
|
1958 | 1968 |
<para> |
1959 | 1969 |
Example: |
b/scripts/gnt-instance | ||
---|---|---|
744 | 744 |
|
745 | 745 |
""" |
746 | 746 |
op = opcodes.OpStartupInstance(instance_name=name, |
747 |
force=opts.force) |
|
747 |
force=opts.force, |
|
748 |
ignore_offline_nodes=opts.ignore_offline) |
|
748 | 749 |
# do not add these parameters to the opcode unless they're defined |
749 | 750 |
if opts.hvparams: |
750 | 751 |
op.hvparams = opts.hvparams |
... | ... | |
782 | 783 |
|
783 | 784 |
""" |
784 | 785 |
return opcodes.OpShutdownInstance(instance_name=name, |
785 |
timeout=opts.timeout) |
|
786 |
timeout=opts.timeout, |
|
787 |
ignore_offline_nodes=opts.ignore_offline) |
|
786 | 788 |
|
787 | 789 |
|
788 | 790 |
def ReplaceDisks(opts, args): |
... | ... | |
1487 | 1489 |
[m_node_opt, m_pri_node_opt, m_sec_node_opt, m_clust_opt, |
1488 | 1490 |
m_node_tags_opt, m_pri_node_tags_opt, m_sec_node_tags_opt, |
1489 | 1491 |
m_inst_tags_opt, m_inst_opt, m_force_multi, TIMEOUT_OPT, SUBMIT_OPT, |
1490 |
DRY_RUN_OPT, PRIORITY_OPT], |
|
1492 |
DRY_RUN_OPT, PRIORITY_OPT, IGNORE_OFFLINE_OPT],
|
|
1491 | 1493 |
"<instance>", "Stops an instance"), |
1492 | 1494 |
'startup': ( |
1493 | 1495 |
GenericManyOps("startup", _StartupInstance), [ArgInstance()], |
1494 | 1496 |
[FORCE_OPT, m_force_multi, m_node_opt, m_pri_node_opt, m_sec_node_opt, |
1495 | 1497 |
m_node_tags_opt, m_pri_node_tags_opt, m_sec_node_tags_opt, |
1496 | 1498 |
m_inst_tags_opt, m_clust_opt, m_inst_opt, SUBMIT_OPT, HVOPTS_OPT, |
1497 |
BACKEND_OPT, DRY_RUN_OPT, PRIORITY_OPT], |
|
1499 |
BACKEND_OPT, DRY_RUN_OPT, PRIORITY_OPT, IGNORE_OFFLINE_OPT],
|
|
1498 | 1500 |
"<instance>", "Starts an instance"), |
1499 | 1501 |
'reboot': ( |
1500 | 1502 |
GenericManyOps("reboot", _RebootInstance), [ArgInstance()], |
Also available in: Unified diff