Revision a0724772
b/lib/client/gnt_node.py | ||
---|---|---|
523 | 523 |
return constants.EXIT_SUCCESS |
524 | 524 |
|
525 | 525 |
|
526 |
def Health(opts, args): |
|
527 |
"""Show health of a node using OOB. |
|
528 |
|
|
529 |
@param opts: the command line options selected by the user |
|
530 |
@type args: list |
|
531 |
@param args: should contain only one element, the name of |
|
532 |
the node to be removed |
|
533 |
@rtype: int |
|
534 |
@return: the desired exit code |
|
535 |
|
|
536 |
""" |
|
537 |
op = opcodes.OpOobCommand(node_names=args, command=constants.OOB_HEALTH) |
|
538 |
result = SubmitOpCode(op, opts=opts) |
|
539 |
|
|
540 |
if opts.no_headers: |
|
541 |
headers = None |
|
542 |
else: |
|
543 |
headers = {"node": "Node", "status": "Status"} |
|
544 |
|
|
545 |
errs = 0 |
|
546 |
data = [] |
|
547 |
for node_result in result: |
|
548 |
(node_tuple, data_tuple) = node_result |
|
549 |
(_, node_name) = node_tuple |
|
550 |
(data_status, data_node) = data_tuple |
|
551 |
if data_status == constants.RS_NORMAL: |
|
552 |
data.append([node_name, "%s=%s" % tuple(data_node[0])]) |
|
553 |
for item, status in data_node[1:]: |
|
554 |
data.append(["", "%s=%s" % (item, status)]) |
|
555 |
else: |
|
556 |
errs += 1 |
|
557 |
data.append([node_name, cli.FormatResultError(data_status)]) |
|
558 |
|
|
559 |
data = GenerateTable(separator=opts.separator, headers=headers, |
|
560 |
fields=["node", "status"], data=data) |
|
561 |
|
|
562 |
for line in data: |
|
563 |
ToStdout(line) |
|
564 |
|
|
565 |
if errs: |
|
566 |
return constants.EXIT_FAILURE |
|
567 |
else: |
|
568 |
return constants.EXIT_SUCCESS |
|
569 |
|
|
570 |
|
|
526 | 571 |
def ListVolumes(opts, args): |
527 | 572 |
"""List logical volumes on node(s). |
528 | 573 |
|
... | ... | |
812 | 857 |
RemoveTags, [ArgNode(min=1, max=1), ArgUnknown()], |
813 | 858 |
[TAG_SRC_OPT, PRIORITY_OPT], |
814 | 859 |
"<node_name> tag...", "Remove tags from the given node"), |
860 |
"health": ( |
|
861 |
Health, ARGS_MANY_NODES, |
|
862 |
[NOHDR_OPT, SEP_OPT, SUBMIT_OPT, PRIORITY_OPT], |
|
863 |
"[<node_name>...]", "List health of node(s) using out-of-band"), |
|
815 | 864 |
} |
816 | 865 |
|
817 | 866 |
|
b/man/gnt-node.rst | ||
---|---|---|
606 | 606 |
This commands calls out to out-of-band management to change the power |
607 | 607 |
state of given node. With ``status`` you get the power status as reported |
608 | 608 |
by the out-of-band managment script. |
609 |
|
|
610 |
HEALTH |
|
611 |
~~~~~~ |
|
612 |
|
|
613 |
**health** [*nodes*] |
|
614 |
|
|
615 |
This commands calls out to out-pf-band management to ask for the health status |
|
616 |
of all or given nodes. The health contains the node name and then the items |
|
617 |
element with their status in a ``item=status`` manner. Where ``item`` is script |
|
618 |
specific and ``status`` can be one of ``OK``, ``WARNING``, ``CRITICAL`` or |
|
619 |
``UNKNOWN``. Items with status ``WARNING`` or ``CRITICAL`` are logged and |
|
620 |
annotated in the command line output. |
b/qa/qa_node.py | ||
---|---|---|
280 | 280 |
AssertCommand(["gnt-node", "power", "cycle", node_name]) |
281 | 281 |
_AssertOobCall(verify_path, "power-cycle %s" % full_node_name) |
282 | 282 |
|
283 |
# This command should fail as it expects output which isn't provided yet
|
|
284 |
# But it should have called the oob helper nevermind
|
|
283 |
# Those commands should fail as they expect output which isn't provided yet
|
|
284 |
# But they should have called the oob helper nevermind
|
|
285 | 285 |
AssertCommand(["gnt-node", "power", "status", node_name], |
286 | 286 |
fail=True) |
287 | 287 |
_AssertOobCall(verify_path, "power-status %s" % full_node_name) |
288 | 288 |
|
289 |
# Data, exit 0 |
|
289 |
AssertCommand(["gnt-node", "health", node_name], |
|
290 |
fail=True) |
|
291 |
_AssertOobCall(verify_path, "health %s" % full_node_name) |
|
292 |
|
|
293 |
AssertCommand(["gnt-node", "health"], fail=True) |
|
294 |
|
|
295 |
# Correct Data, exit 0 |
|
290 | 296 |
_UpdateOobFile(data_path, serializer.DumpJson({ "powered": True })) |
291 | 297 |
|
292 | 298 |
AssertCommand(["gnt-node", "power", "status", node_name]) |
293 | 299 |
_AssertOobCall(verify_path, "power-status %s" % full_node_name) |
294 | 300 |
|
301 |
_UpdateOobFile(data_path, serializer.DumpJson([["temp", "OK"], |
|
302 |
["disk0", "CRITICAL"]])) |
|
303 |
|
|
304 |
AssertCommand(["gnt-node", "health", node_name]) |
|
305 |
_AssertOobCall(verify_path, "health %s" % full_node_name) |
|
306 |
|
|
307 |
AssertCommand(["gnt-node", "health"]) |
|
308 |
|
|
309 |
|
|
310 |
# Those commands should fail as they expect no data regardless of exit 0 |
|
295 | 311 |
AssertCommand(["gnt-node", "power", "on", node_name], fail=True) |
296 | 312 |
_AssertOobCall(verify_path, "power-on %s" % full_node_name) |
297 | 313 |
|
... | ... | |
323 | 339 |
fail=True) |
324 | 340 |
_AssertOobCall(verify_path, "power-status %s" % full_node_name) |
325 | 341 |
|
342 |
AssertCommand(["gnt-node", "health", node_name], |
|
343 |
fail=True) |
|
344 |
_AssertOobCall(verify_path, "health %s" % full_node_name) |
|
345 |
|
|
346 |
AssertCommand(["gnt-node", "health"], fail=True) |
|
347 |
|
|
326 | 348 |
# No data, exit 1 (all should fail) |
327 | 349 |
_UpdateOobFile(data_path, "") |
328 | 350 |
AssertCommand(["gnt-node", "power", "on", node_name], fail=True) |
... | ... | |
341 | 363 |
fail=True) |
342 | 364 |
_AssertOobCall(verify_path, "power-status %s" % full_node_name) |
343 | 365 |
|
366 |
AssertCommand(["gnt-node", "health", node_name], |
|
367 |
fail=True) |
|
368 |
_AssertOobCall(verify_path, "health %s" % full_node_name) |
|
369 |
|
|
370 |
AssertCommand(["gnt-node", "health"], fail=True) |
|
371 |
|
|
344 | 372 |
# Different OOB script for node |
345 | 373 |
verify_path2 = qa_utils.UploadData(master["primary"], "") |
346 | 374 |
oob_script = ("#!/bin/sh\n" |
Also available in: Unified diff