Revision 83180411

b/qa/ganeti-qa.py
34 34
import qa_config
35 35
import qa_daemon
36 36
import qa_env
37
import qa_error
37 38
import qa_group
38 39
import qa_instance
39 40
import qa_node
......
391 392
  RunTest(qa_daemon.TestResumeWatcher)
392 393

  
393 394

  
395
def RunSingleHomedHardwareFailureTests(instance, pnode):
396
  """Test hardware failure recovery for single-homed instances.
397

  
398
  """
399
  if qa_config.TestEnabled("instance-recreate-disks"):
400
    othernode = qa_config.AcquireNode(exclude=[pnode])
401
    try:
402
      RunTest(qa_instance.TestRecreateDisks,
403
              instance, pnode, None, [othernode])
404
    finally:
405
      qa_config.ReleaseNode(othernode)
406

  
407

  
394 408
def RunHardwareFailureTests(instance, pnode, snode):
395 409
  """Test cluster internal hardware failure recovery.
396 410

  
......
412 426
    finally:
413 427
      qa_config.ReleaseNode(othernode)
414 428

  
429
  if qa_config.TestEnabled("instance-recreate-disks"):
430
    othernode1 = qa_config.AcquireNode(exclude=[pnode, snode])
431
    try:
432
      othernode2 = qa_config.AcquireNode(exclude=[pnode, snode, othernode1])
433
    except qa_error.OutOfNodesError:
434
      # Let's reuse one of the nodes if the cluster is not big enough
435
      othernode2 = pnode
436
    try:
437
      RunTest(qa_instance.TestRecreateDisks,
438
              instance, pnode, snode, [othernode1, othernode2])
439
    finally:
440
      qa_config.ReleaseNode(othernode1)
441
      if othernode2 != pnode:
442
        qa_config.ReleaseNode(othernode2)
443

  
415 444
  RunTestIf("node-evacuate", qa_node.TestNodeEvacuate, pnode, snode)
416 445

  
417 446
  RunTestIf("node-failover", qa_node.TestNodeFailover, pnode, snode)
......
477 506
      RunExportImportTests(instance, pnode, None)
478 507
      RunDaemonTests(instance)
479 508
      RunRepairDiskSizes()
509
      RunSingleHomedHardwareFailureTests(instance, pnode)
480 510
      RunTest(qa_instance.TestInstanceRemove, instance)
481 511
      del instance
482 512

  
b/qa/qa-sample.json
140 140
    "# on whether they support the `gnt-instance console' command.": null,
141 141
    "instance-console": false,
142 142

  
143
    "# Disabled by default because it takes rather long": null,
143
    "# Disabled by default because they take rather long": null,
144 144
    "instance-replace-disks": false,
145
    "instance-recreate-disks": false,
145 146

  
146 147
    "# Whether to test the tools/move-instance utility": null,
147 148
    "inter-cluster-instance-move": false,
b/qa/qa_instance.py
433 433
  AssertCommand(["gnt-instance", "start", instance["name"]])
434 434

  
435 435

  
436
def _AssertRecreateDisks(cmdargs, instance, fail=False, check=True,
437
                         destroy=True):
438
  """Execute gnt-instance recreate-disks and check the result
439

  
440
  @param cmdargs: Arguments (instance name excluded)
441
  @param instance: Instance to operate on
442
  @param fail: True if the command is expected to fail
443
  @param check: If True and fail is False, check that the disks work
444
  @prama destroy: If True, destroy the old disks first
445

  
446
  """
447
  if destroy:
448
    _DestroyInstanceVolumes(instance)
449
  AssertCommand((["gnt-instance", "recreate-disks"] + cmdargs +
450
                 [instance["name"]]), fail)
451
  if not fail and check:
452
    # Quick check that the disks are there
453
    AssertCommand(["gnt-instance", "activate-disks", instance["name"]])
454
    AssertCommand(["gnt-instance", "deactivate-disks", instance["name"]])
455

  
456
@InstanceCheck(INST_UP, INST_UP, FIRST_ARG)
457
def TestRecreateDisks(instance, pnode, snode, othernodes):
458
  """gnt-instance recreate-disks
459

  
460
  @param instance: Instance to work on
461
  @param pnode: Primary node
462
  @param snode: Secondary node, or None for sigle-homed instances
463
  @param othernodes: list/tuple of nodes where to temporarily recreate disks
464

  
465
  """
466
  other_seq = ":".join([n["primary"] for n in othernodes])
467
  orig_seq = pnode["primary"]
468
  if snode:
469
    orig_seq = orig_seq + ":" + snode["primary"]
470
  # This fails beacuse the instance is running
471
  _AssertRecreateDisks(["-n", other_seq], instance, fail=True, destroy=False)
472
  AssertCommand(["gnt-instance", "stop", instance["name"]])
473
  # Disks exist: this should fail
474
  _AssertRecreateDisks([], instance, fail=True, destroy=False)
475
  # Recreate disks in place
476
  _AssertRecreateDisks([], instance)
477
  # Move disks away
478
  _AssertRecreateDisks(["-n", other_seq], instance)
479
  # Move disks back
480
  _AssertRecreateDisks(["-n", orig_seq], instance, check=False)
481
  # This and InstanceCheck decoration check that the disks are working
482
  AssertCommand(["gnt-instance", "reinstall", "-f", instance["name"]])
483
  AssertCommand(["gnt-instance", "start", instance["name"]])
484

  
485

  
436 486
@InstanceCheck(INST_UP, INST_UP, FIRST_ARG)
437 487
def TestInstanceExport(instance, node):
438 488
  """gnt-backup export -n ..."""

Also available in: Unified diff