Beispiel #1
0
 def test_invalid_operstate_for_action(self, mrapi):
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     self.assertRaises(faults.BadRequest, servers.start, vm)
     vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
     self.assertRaises(faults.BadRequest, servers.stop, vm)
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     flavor = mfactory.FlavorFactory()
     self.assertRaises(faults.BadRequest, servers.resize, vm, flavor)
     # Check that connect/disconnect is allowed only in STOPPED vms
     # if hotplug is disabled.
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     network = mfactory.NetworkFactory(state="ACTIVE")
     with override_settings(settings, GANETI_USE_HOTPLUG=False):
         self.assertRaises(faults.BadRequest, servers.connect, vm, network)
         self.assertRaises(faults.BadRequest, servers.disconnect, vm, network)
     # test valid
     vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
     mrapi().StartupInstance.return_value = 1
     with mocked_quotaholder():
         servers.start(vm)
     vm.task = None
     vm.task_job_id = None
     vm.save()
     with mocked_quotaholder():
         quotas.accept_resource_serial(vm)
     mrapi().RebootInstance.return_value = 1
     with mocked_quotaholder():
         servers.reboot(vm, "HARD")
Beispiel #2
0
 def test_task_after(self, mrapi):
     return
     vm = mfactory.VirtualMachineFactory()
     mrapi().StartupInstance.return_value = 1
     mrapi().ShutdownInstance.return_value = 2
     mrapi().RebootInstance.return_value = 2
     with mocked_quotaholder():
         vm.task = None
         vm.operstate = "STOPPED"
         vm.save()
         servers.start(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "START")
         self.assertEqual(vm.task_job_id, 1)
     with mocked_quotaholder():
         vm.task = None
         vm.operstate = "STARTED"
         vm.save()
         servers.stop(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "STOP")
         self.assertEqual(vm.task_job_id, 2)
     with mocked_quotaholder():
         vm.task = None
         vm.save()
         servers.reboot(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "REBOOT")
         self.assertEqual(vm.task_job_id, 3)
Beispiel #3
0
 def test_invalid_operstate_for_action(self, mrapi):
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     self.assertRaises(faults.BadRequest, servers.start, vm)
     vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
     self.assertRaises(faults.BadRequest, servers.stop, vm)
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     flavor = mfactory.FlavorFactory()
     self.assertRaises(faults.BadRequest, servers.resize, vm, flavor)
     # Check that connect/disconnect is allowed only in STOPPED vms
     # if hotplug is disabled.
     vm = mfactory.VirtualMachineFactory(operstate="STARTED")
     network = mfactory.NetworkFactory(state="ACTIVE")
     with override_settings(settings, GANETI_USE_HOTPLUG=False):
         self.assertRaises(faults.BadRequest, servers.connect, vm, network)
         self.assertRaises(faults.BadRequest, servers.disconnect, vm,
                           network)
     #test valid
     vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
     mrapi().StartupInstance.return_value = 1
     with mocked_quotaholder():
         servers.start(vm)
     vm.task = None
     vm.task_job_id = None
     vm.save()
     with mocked_quotaholder():
         quotas.accept_resource_serial(vm)
     mrapi().RebootInstance.return_value = 1
     with mocked_quotaholder():
         servers.reboot(vm, "HARD")
Beispiel #4
0
 def test_task_after(self, mrapi):
     return
     vm = mfactory.VirtualMachineFactory()
     mrapi().StartupInstance.return_value = 1
     mrapi().ShutdownInstance.return_value = 2
     mrapi().RebootInstance.return_value = 2
     with mocked_quotaholder():
         vm.task = None
         vm.operstate = "STOPPED"
         vm.save()
         servers.start(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "START")
         self.assertEqual(vm.task_job_id, 1)
     with mocked_quotaholder():
         vm.task = None
         vm.operstate = "STARTED"
         vm.save()
         servers.stop(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "STOP")
         self.assertEqual(vm.task_job_id, 2)
     with mocked_quotaholder():
         vm.task = None
         vm.save()
         servers.reboot(vm.id, credentials=self.credentials)
         self.assertEqual(vm.task, "REBOOT")
         self.assertEqual(vm.task_job_id, 3)
Beispiel #5
0
def start(request, server_id, args):
    # Normal Response Code: 202
    # Error Response Codes: serviceUnavailable (503),
    #                       itemNotFound (404)
    credentials = request.credentials
    servers.start(server_id, credentials=credentials)

    log.info("User %s started VM %s", credentials.userid, server_id)

    return HttpResponse(status=202)
Beispiel #6
0
def start(request, server_id, args):
    # Normal Response Code: 202
    # Error Response Codes: serviceUnavailable (503),
    #                       itemNotFound (404)
    credentials = request.credentials
    servers.start(server_id, credentials=credentials)

    log.info("User %s started VM %s", credentials.userid, server_id)

    return HttpResponse(status=202)
Beispiel #7
0
    def test_commission(self, mrapi):
        vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
        # Still pending
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=200,
                                                      resolved=False,
                                                      pending=True)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            with self.assertRaises(quotas.ResolveError):
                servers.start(vm.id, credentials=self.credentials)
        # Not pending, rejct
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=400,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=False)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm.id, credentials=self.credentials)
            m.resolve_commissions.assert_called_once_with([],
                                                          [serial.serial])
            self.assertTrue(m.issue_one_commission.called)
        # Not pending, accept
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=600,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=True)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm.id, credentials=self.credentials)
            m.resolve_commissions.assert_called_once_with([serial.serial],
                                                          [])
            self.assertTrue(m.issue_one_commission.called)

        mrapi().StartupInstance.side_effect = ValueError
        vm.task = None
        vm.serial = None
        vm.save()
        # Test reject if Ganeti erro
        with mocked_quotaholder() as m:
            try:
                servers.start(vm.id, credentials=self.credentials)
            except Exception:
                (accept, reject), kwargs = m.resolve_commissions.call_args
                self.assertEqual(accept, [])
                self.assertEqual(len(reject), 1)
                self.assertEqual(kwargs, {})
            else:
                raise AssertionError("Starting a server should raise an"
                                     " exception.")
Beispiel #8
0
    def test_commission(self, mrapi):
        vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
        # Still pending
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=200,
                                                      resolved=False,
                                                      pending=True)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            with self.assertRaises(quotas.ResolveError):
                servers.start(vm.id, credentials=self.credentials)
        # Not pending, rejct
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=400,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=False)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm.id, credentials=self.credentials)
            m.resolve_commissions.assert_called_once_with([], [serial.serial])
            self.assertTrue(m.issue_one_commission.called)
        # Not pending, accept
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=600,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=True)
        vm.save()
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm.id, credentials=self.credentials)
            m.resolve_commissions.assert_called_once_with([serial.serial], [])
            self.assertTrue(m.issue_one_commission.called)

        mrapi().StartupInstance.side_effect = ValueError
        vm.task = None
        vm.serial = None
        vm.save()
        # Test reject if Ganeti erro
        with mocked_quotaholder() as m:
            try:
                servers.start(vm.id, credentials=self.credentials)
            except Exception:
                (accept, reject), kwargs = m.resolve_commissions.call_args
                self.assertEqual(accept, [])
                self.assertEqual(len(reject), 1)
                self.assertEqual(kwargs, {})
            else:
                raise AssertionError("Starting a server should raise an"
                                     " exception.")
Beispiel #9
0
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("Please provide a server ID")

        server = get_resource("server", args[0], for_update=True)

        new_name = options.get("name", None)
        if new_name is not None:
            old_name = server.name
            server = servers.rename(server, new_name)
            self.stdout.write("Renamed server '%s' from '%s' to '%s'\n" %
                              (server, old_name, new_name))

        suspended = options.get("suspended", None)
        if suspended is not None:
            suspended = parse_bool(suspended)
            server.suspended = suspended
            server.save()
            self.stdout.write("Set server '%s' as suspended=%s\n" %
                              (server, suspended))

        new_owner = options.get('user')
        if new_owner is not None:
            if "@" in new_owner:
                raise CommandError("Invalid user UUID.")
            if new_owner == server.userid:
                self.stdout.write("%s is already server owner.\n" % new_owner)
            else:
                servers.change_owner(server, new_owner)
                self.stdout.write(
                    "WARNING: User quotas should be out of sync now,"
                    " run `snf-manage reconcile-resources-cyclades'"
                    " to review and update them.\n")

        wait = parse_bool(options["wait"])
        new_flavor_id = options.get("flavor")
        if new_flavor_id is not None:
            new_flavor = get_resource("flavor", new_flavor_id)
            old_flavor = server.flavor
            msg = "Resizing server '%s' from flavor '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_flavor, new_flavor))
            server = servers.resize(server, new_flavor)
            wait_server_task(server, wait, stdout=self.stdout)

        action = options.get("action")
        if action is not None:
            if action == "start":
                server = servers.start(server)
            elif action == "stop":
                server = servers.stop(server)
            elif action == "reboot_hard":
                server = servers.reboot(server, reboot_type="HARD")
            elif action == "reboot_soft":
                server = servers.reboot(server, reboot_type="SOFT")
            else:
                raise CommandError("Unknown action.")
            wait_server_task(server, wait, stdout=self.stdout)
Beispiel #10
0
def vm_start(request, vm_id):
    logging.info("VM %s start by %s", vm_id, request.user_uniq)
    vm = VirtualMachine.objects.get(pk=vm_id)
    account = vm.userid
    error = None
    try:
        jobId = servers_backend.start(vm)
    except Exception, e:
        error = e.message
Beispiel #11
0
def start(request, vm, args):
    # Normal Response Code: 202
    # Error Response Codes: serviceUnavailable (503),
    #                       itemNotFound (404)
    vm = servers.start(vm)

    log.info("User %s started VM %s", request.user_uniq, vm.id)

    return HttpResponse(status=202)
Beispiel #12
0
def vm_start(request, vm_id):
    logging.info("VM %s start by %s", vm_id, request.user_uniq)
    vm = VirtualMachine.objects.get(pk=vm_id)
    account = vm.userid
    error = None
    try:
        jobId = servers_backend.start(vm)
    except Exception, e:
        error = e.message
Beispiel #13
0
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("Please provide a server ID")

        server = get_resource("server", args[0], for_update=True)

        new_name = options.get("name", None)
        if new_name is not None:
            old_name = server.name
            server = servers.rename(server, new_name)
            self.stdout.write("Renamed server '%s' from '%s' to '%s'\n" %
                              (server, old_name, new_name))

        suspended = options.get("suspended", None)
        if suspended is not None:
            suspended = parse_bool(suspended)
            server.suspended = suspended
            server.save()
            self.stdout.write("Set server '%s' as suspended=%s\n" %
                              (server, suspended))

        new_owner = options.get('user')
        if new_owner is not None:
            if "@" in new_owner:
                raise CommandError("Invalid user UUID.")
            old_owner = server.userid
            server.userid = new_owner
            server.save()
            msg = "Changed the owner of server '%s' from '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_owner, new_owner))

        wait = parse_bool(options["wait"])
        new_flavor_id = options.get("flavor")
        if new_flavor_id is not None:
            new_flavor = get_resource("flavor", new_flavor_id)
            old_flavor = server.flavor
            msg = "Resizing server '%s' from flavor '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_flavor, new_flavor))
            server = servers.resize(server, new_flavor)
            wait_server_task(server, wait, stdout=self.stdout)

        action = options.get("action")
        if action is not None:
            if action == "start":
                server = servers.start(server)
            elif action == "stop":
                server = servers.stop(server)
            elif action == "reboot_hard":
                server = servers.reboot(server, reboot_type="HARD")
            elif action == "reboot_stof":
                server = servers.reboot(server, reboot_type="SOFT")
            else:
                raise CommandError("Unknown action.")
            wait_server_task(server, wait, stdout=self.stdout)
Beispiel #14
0
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("Please provide a server ID")

        server = get_vm(args[0], for_update=True)

        new_name = options.get("name", None)
        if new_name is not None:
            old_name = server.name
            server = servers.rename(server, new_name)
            self.stdout.write("Renamed server '%s' from '%s' to '%s'\n" %
                              (server, old_name, new_name))

        suspended = options.get("suspended", None)
        if suspended is not None:
            suspended = parse_bool(suspended)
            server.suspended = suspended
            server.save()
            self.stdout.write("Set server '%s' as suspended=%s\n" %
                              (server, suspended))

        new_owner = options.get('owner')
        if new_owner is not None:
            if "@" in new_owner:
                raise CommandError("Invalid owner UUID.")
            old_owner = server.userid
            server.userid = new_owner
            server.save()
            msg = "Changed the owner of server '%s' from '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_owner, new_owner))

        wait = parse_bool(options["wait"])
        new_flavor_id = options.get("flavor")
        if new_flavor_id is not None:
            new_flavor = get_flavor(new_flavor_id)
            old_flavor = server.flavor
            msg = "Resizing server '%s' from flavor '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_flavor, new_flavor))
            server = servers.resize(server, new_flavor)
            wait_server_task(server, wait, stdout=self.stdout)

        action = options.get("action")
        if action is not None:
            if action == "start":
                server = servers.start(server)
            elif action == "stop":
                server = servers.stop(server)
            elif action == "reboot_hard":
                server = servers.reboot(server, reboot_type="HARD")
            elif action == "reboot_stof":
                server = servers.reboot(server, reboot_type="SOFT")
            else:
                raise CommandError("Unknown action.")
            wait_server_task(server, wait, stdout=self.stdout)
Beispiel #15
0
    def test_commission(self, mrapi):
        vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
        # Still pending
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=200,
                                                      resolved=False,
                                                      pending=True)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            with self.assertRaises(quotas.ResolveError):
                servers.start(vm)
        # Not pending, rejct
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=400,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=False)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm)
            m.resolve_commissions.assert_called_once_with([], [serial.serial])
            self.assertTrue(m.issue_one_commission.called)
        # Not pending, accept
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=600,
                                                      resolved=False,
                                                      pending=False,
                                                      accept=True)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm)
            m.resolve_commissions.assert_called_once_with([serial.serial], [])
            self.assertTrue(m.issue_one_commission.called)

        mrapi().StartupInstance.side_effect = ValueError
        vm.task = None
        vm.serial = None
        # Test reject if Ganeti erro
        with mocked_quotaholder() as m:
            try:
                servers.start(vm)
            except:
                m.resolve_commissions\
                 .assert_called_once_with([], [vm.serial.serial])
Beispiel #16
0
    def test_commission(self, mrapi):
        vm = mfactory.VirtualMachineFactory(operstate="STOPPED")
        # Still pending
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=200, resolved=False, pending=True)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            with self.assertRaises(quotas.ResolveError):
                servers.start(vm)
        # Not pending, rejct
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=400, resolved=False, pending=False, accept=False)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm)
            m.resolve_commissions.assert_called_once_with([], [serial.serial])
            self.assertTrue(m.issue_one_commission.called)
        # Not pending, accept
        vm.task = None
        vm.serial = mfactory.QuotaHolderSerialFactory(serial=600, resolved=False, pending=False, accept=True)
        serial = vm.serial
        mrapi().StartupInstance.return_value = 1
        with mocked_quotaholder() as m:
            servers.start(vm)
            m.resolve_commissions.assert_called_once_with([serial.serial], [])
            self.assertTrue(m.issue_one_commission.called)

        mrapi().StartupInstance.side_effect = ValueError
        vm.task = None
        vm.serial = None
        # Test reject if Ganeti erro
        with mocked_quotaholder() as m:
            try:
                servers.start(vm)
            except:
                m.resolve_commissions.assert_called_once_with([], [vm.serial.serial])
Beispiel #17
0
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("Please provide a server ID")

        server_id = args[0]
        server = get_resource("server", server_id)

        credentials = Credentials("snf-manage", is_admin=True)
        new_name = options.get("name", None)
        if new_name is not None:
            old_name = server.name
            server = servers.rename(server_id, new_name, credentials)
            self.stdout.write("Renamed server '%s' from '%s' to '%s'\n" %
                              (server, old_name, new_name))

        suspended = options.get("suspended", None)
        if suspended is not None:
            suspended = parse_bool(suspended)
            server = servers.suspend(server_id, suspended, credentials)
            self.stdout.write("Set server '%s' as suspended=%s\n" %
                              (server, suspended))

        new_owner = options.get('user')
        if new_owner is not None:
            if "@" in new_owner:
                raise CommandError("Invalid user UUID.")
            if new_owner == server.userid:
                self.stdout.write("%s is already server owner.\n" % new_owner)
            else:
                servers.change_owner(server_id, new_owner, credentials)
                self.stdout.write(
                    "WARNING: User quotas should be out of sync now,"
                    " run `snf-manage reconcile-resources-cyclades'"
                    " to review and update them.\n")

        wait = parse_bool(options["wait"])
        new_flavor_id = options.get("flavor")
        if new_flavor_id is not None:
            new_flavor = get_resource("flavor", new_flavor_id)
            old_flavor = server.flavor
            msg = "Resizing server '%s' from flavor '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_flavor, new_flavor))
            server = servers.resize(server_id, new_flavor, credentials)
            wait_server_task(server, wait, stdout=self.stdout)

        action = options.get("action")
        if action is not None:
            if action == "start":
                server = servers.start(server_id, credentials=credentials)
            elif action == "stop":
                server = servers.stop(server_id, credentials=credentials)
            elif action == "reboot_hard":
                server = servers.reboot(server_id, reboot_type="HARD",
                                        credentials=credentials)
            elif action == "reboot_soft":
                server = servers.reboot(server_id, reboot_type="SOFT",
                                        credentials=credentials)
            elif action == "rescue":
                server = servers.rescue(server_id, credentials=credentials)
            elif action == "unrescue":
                server = servers.unrescue(server_id, credentials=credentials)
            else:
                raise CommandError("Unknown action.")
            wait_server_task(server, wait, stdout=self.stdout)
Beispiel #18
0
def start(request, vm, args):
    # Normal Response Code: 202
    # Error Response Codes: serviceUnavailable (503),
    #                       itemNotFound (404)
    vm = servers.start(vm)
    return HttpResponse(status=202)
Beispiel #19
0
def start(request, vm, args):
    # Normal Response Code: 202
    # Error Response Codes: serviceUnavailable (503),
    #                       itemNotFound (404)
    vm = servers.start(vm)
    return HttpResponse(status=202)
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("Please provide a server ID")

        server = get_resource("server", args[0], for_update=True)

        new_name = options.get("name", None)
        if new_name is not None:
            old_name = server.name
            server = servers.rename(server, new_name)
            self.stdout.write("Renamed server '%s' from '%s' to '%s'\n" %
                              (server, old_name, new_name))

        suspended = options.get("suspended", None)
        if suspended is not None:
            suspended = parse_bool(suspended)
            server.suspended = suspended
            server.save()
            self.stdout.write("Set server '%s' as suspended=%s\n" %
                              (server, suspended))

        new_owner = options.get('user')
        if new_owner is not None:
            if "@" in new_owner:
                raise CommandError("Invalid user UUID.")
            old_owner = server.userid
            server.userid = new_owner
            old_project = server.project
            server.project = new_owner
            server.save()
            msg = "Changed the owner of server '%s' from '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_owner, new_owner))
            msg = "Changed the project of server '%s' from '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_project, new_owner))
            for vol in server.volumes.filter(
                    userid=old_owner).select_for_update():
                vol.userid = new_owner
                vol_old_project = vol.project
                vol.project = new_owner
                vol.save()
                msg = "Changed the owner of volume '%s' from '%s' to '%s'.\n"
                self.stdout.write(msg % (vol, old_owner, new_owner))
                msg = "Changed the project of volume '%s' from '%s' to '%s'.\n"
                self.stdout.write(msg % (vol, vol_old_project, new_owner))
            self.stdout.write("WARNING: User quotas should be out of sync now,"
                              " run `snf-manage reconcile-resources-cyclades'"
                              " to review and update them.\n")

        wait = parse_bool(options["wait"])
        new_flavor_id = options.get("flavor")
        if new_flavor_id is not None:
            new_flavor = get_resource("flavor", new_flavor_id)
            old_flavor = server.flavor
            msg = "Resizing server '%s' from flavor '%s' to '%s'.\n"
            self.stdout.write(msg % (server, old_flavor, new_flavor))
            server = servers.resize(server, new_flavor)
            wait_server_task(server, wait, stdout=self.stdout)

        action = options.get("action")
        if action is not None:
            if action == "start":
                server = servers.start(server)
            elif action == "stop":
                server = servers.stop(server)
            elif action == "reboot_hard":
                server = servers.reboot(server, reboot_type="HARD")
            elif action == "reboot_stof":
                server = servers.reboot(server, reboot_type="SOFT")
            else:
                raise CommandError("Unknown action.")
            wait_server_task(server, wait, stdout=self.stdout)