Esempio n. 1
0
class SnapshotsController(wsgi.Controller):
    """The Snapshots API controller for the SG-Service."""

    _view_builder_class = SnapshotViewBuilder

    def __init__(self):
        self.service_api = ServiceAPI()
        super(SnapshotsController, self).__init__()

    def _get_snapshot_filter_options(self):
        return CONF.query_snapshot_filters

    def show(self, req, id):
        """Return data about the given snapshots."""
        LOG.info(_LI("Show snapshot with id: %s"), id)
        context = req.environ['sgservice.context']
        snapshot = self.service_api.get_snapshot(context, id)
        return self._view_builder.detail(req, snapshot)

    def delete(self, req, id):
        """Delete a snapshot."""
        LOG.info(_LI("Delete snapshot with id: %s"), id)
        context = req.environ['sgservice.context']
        snapshot = self.service_api.get_snapshot(context, id)
        self.service_api.delete_snapshot(context, snapshot)
        return webob.Response(status_int=202)

    def index(self, req):
        """Returns a list of snapshots, transformed through view builder."""
        LOG.info(_LI("Show snapshot list"))
        context = req.environ['sgservice.context']
        params = req.params.copy()
        marker, limit, offset = common.get_pagination_params(params)
        sort_keys, sort_dirs = common.get_sort_params(params)
        filters = params

        utils.remove_invaild_filter_options(
            context, filters, self._get_snapshot_filter_options())
        utils.check_filters(filters)

        if 'name' in sort_keys:
            sort_keys[sort_keys.index('name')] = 'display_name'

        if 'name' in filters:
            filters['display_name'] = filters.pop('name')

        snapshots = self.service_api.get_all_snapshots(context,
                                                       marker=marker,
                                                       limit=limit,
                                                       sort_keys=sort_keys,
                                                       sort_dirs=sort_dirs,
                                                       filters=filters,
                                                       offset=offset)

        retval_snapshots = self._view_builder.detail_list(req, snapshots)
        LOG.info(_LI("Show snapshot list request issued successfully."))
        return retval_snapshots

    def create(self, req, body):
        """Creates a new snapshot."""
        LOG.debug('Create snapshot request body: %s', body)
        context = req.environ['sgservice.context']
        snapshot = body['snapshot']

        volume_id = snapshot.get('volume_id', None)
        if volume_id is None:
            msg = _('Incorrect request body format')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        name = snapshot.get('name', None)
        description = snapshot.get('description', None)
        if description is None:
            description = 'snapshot-%s' % volume_id
        checkpoint_id = snapshot.get('checkpoint_id', None)

        volume = self.service_api.get(context, volume_id)
        snapshot = self.service_api.create_snapshot(context, name, description,
                                                    volume, checkpoint_id)
        return self._view_builder.detail(req, snapshot)

    def update(self, req, id, body):
        """Update a snapshot."""
        LOG.info(_LI("Update snapshot with id: %s"), id)
        context = req.environ['sgservice.context']
        if not body:
            msg = _("Missing request body")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        if 'snapshot' not in body:
            msg = (_("Missing required element '%s' in request body"),
                   'snapshot')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        snapshot = body['snapshot']
        update_dict = {}

        valid_update_keys = (
            'name',
            'description',
            'display_name',
            'display_description',
        )
        for key in valid_update_keys:
            if key in snapshot:
                update_dict[key] = snapshot[key]
        self.validate_name_and_description(update_dict)
        if 'name' in update_dict:
            update_dict['display_name'] = update_dict.pop('name')
        if 'description' in update_dict:
            update_dict['display_description'] = update_dict.pop('description')

        snapshot = self.service_api.get_snapshot(context, id)
        snapshot.update(update_dict)
        snapshot.save()
        return self._view_builder.detail(req, snapshot)

    @wsgi.action('rollback')
    def rollback(self, req, id, body):
        """Rollback a snapshot to volume"""
        LOG.info(_LI("Rollback snapshot with id: %s"), id)
        context = req.environ['sgservice.context']
        snapshot = self.service_api.get_snapshot(context, id)
        rollback = self.service_api.rollback_snapshot(context, snapshot)
        return self._view_builder.rollback_summary(req, rollback)

    @wsgi.action('reset_status')
    def reset_status(self, req, id, body):
        """reset snapshot status"""
        LOG.info(_LI("Reset snapshot status, id: %s"), id)
        status = body['reset_status'].get('status',
                                          fields.SnapshotStatus.AVAILABLE)
        if status not in fields.SnapshotStatus.ALL:
            msg = _("Invalid status provided.")
            LOG.error(msg)
            raise exception.InvalidStatus(status=status)

        context = req.environ['sgservice.context']
        snapshot = self.service_api.get_snapshot(context, id)
        snapshot.status = status
        snapshot.save()
        return webob.Response(status_int=202)
Esempio n. 2
0
 def __init__(self):
     self.service_api = ServiceAPI()
     super(SnapshotsController, self).__init__()
Esempio n. 3
0
class VolumesController(wsgi.Controller):
    """The Volumes API controller for the SG-Service."""

    _view_builder_class = VolumeViewBuilder

    def __init__(self):
        self.service_api = ServiceAPI()
        super(VolumesController, self).__init__()

    def _get_volume_filter_options(self):
        return CONF.query_volume_filters

    def show(self, req, id):
        """Return data about the given volumes."""
        LOG.info(_LI("Show volume with id: %s"), id)
        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)
        return self._view_builder.detail(req, volume)

    def delete(self, req, id):
        """Delete a sg volume."""
        LOG.info(_LI("Delete sg volume, volume_id: %s"), id)
        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)
        self.service_api.delete(context, volume)
        return webob.Response(status_int=202)

    def index(self, req):
        """Returns a list of volumes, transformed through view builder."""
        LOG.info(_LI("Show volume list"))
        context = req.environ['sgservice.context']
        params = req.params.copy()
        marker, limit, offset = common.get_pagination_params(params)
        sort_keys, sort_dirs = common.get_sort_params(params)
        filters = params

        utils.remove_invaild_filter_options(context, filters,
                                            self._get_volume_filter_options())
        utils.check_filters(filters)

        if 'name' in sort_keys:
            sort_keys[sort_keys.index('name')] = 'display_name'

        if 'name' in filters:
            filters['display_name'] = filters.pop('name')

        volumes = self.service_api.get_all(context,
                                           marker=marker,
                                           limit=limit,
                                           sort_keys=sort_keys,
                                           sort_dirs=sort_dirs,
                                           filters=filters,
                                           offset=offset)

        retval_volumes = self._view_builder.detail_list(req, volumes)
        LOG.info(_LI("Show volume list request issued successfully."))
        return retval_volumes

    def create(self, req, body):
        """Creates a new volume from snapshot or checkpoint."""
        LOG.debug('Create volume from snapshot, request body: %s', body)
        context = req.environ['sgservice.context']
        volume = body['volume']

        volume_type = volume.get('volume_type', None)
        availability_zone = volume.get('availability_zone', None)
        volume_id = volume.get('volume_id', None)
        size = volume.get('size', None)

        # create from snapshot
        snapshot_id = volume.get('snapshot_id')
        if snapshot_id is not None:
            name = volume.get('name', 'volume-%s' % snapshot_id)
            description = volume.get('description', name)
            snapshot = self.service_api.get_snapshot(context, snapshot_id)
            volume = self.service_api.create_volume(
                context,
                snapshot=snapshot,
                volume_type=volume_type,
                availability_zone=availability_zone,
                description=description,
                name=name,
                volume_id=volume_id,
                size=size)
            return self._view_builder.detail(req, volume)

        # create from checkpoint
        checkpoint_id = volume.get('checkpoint_id')
        if checkpoint_id is not None:
            name = volume.get('name', 'volume-%s' % checkpoint_id)
            description = volume.get('description', name)
            checkpoint = self.service_api.get_checkpoint(
                context, checkpoint_id)
            volume = self.service_api.create_volume(
                context,
                checkpoint=checkpoint,
                volume_type=volume_type,
                availability_zone=availability_zone,
                description=description,
                name=name,
                volume_id=volume_id)
            return self._view_builder.detail(req, volume)

        msg = _('Incorrect request body format, create volume must specified '
                'a snapshot or checkpoint')
        raise webob.exc.HTTPBadRequest(explanation=msg)

    def update(self, req, id, body):
        """Update a volume."""
        LOG.info(_LI("Update snapshot with id: %s"), id)
        context = req.environ['sgservice.context']
        if not body:
            msg = _("Missing request body")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        if 'volume' not in body:
            msg = (_("Missing required element '%s' in request body"),
                   'volume')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        volume = body['volume']
        update_dict = {}

        valid_update_keys = (
            'name',
            'description',
            'display_name',
            'display_description',
        )
        for key in valid_update_keys:
            if key in volume:
                update_dict[key] = volume[key]
        self.validate_name_and_description(update_dict)
        if 'name' in update_dict:
            update_dict['display_name'] = update_dict.pop('name')
        if 'description' in update_dict:
            update_dict['display_description'] = update_dict.pop('description')

        volume = self.service_api.get(context, id)
        volume.update(update_dict)
        volume.save()
        return self._view_builder.detail(req, volume)

    @wsgi.action('enable')
    def enable(self, req, id, body):
        """Enable-SG a available volume."""
        LOG.debug('Enable volume SG, volume_id: %s', id)
        context = req.environ['sgservice.context']
        params = body['enable']
        params = {} if params is None else params

        name = params.get('name', None)
        description = params.get('description', None)
        metadata = params.get('metadata', None)
        volume = self.service_api.enable_sg(context,
                                            id,
                                            name=name,
                                            description=description,
                                            metadata=metadata)
        return self._view_builder.detail(req, volume)

    @wsgi.action('disable')
    def disable(self, req, id, body):
        """Disable a enabled-volume."""
        LOG.info(_LI("Disable volume SG, volume_id: %s"), id)
        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)
        volume = self.service_api.disable_sg(context, volume)
        return self._view_builder.detail(req, volume)

    @wsgi.action('attach')
    def attach(self, req, id, body):
        """Add sg-volume attachment metadata."""
        LOG.info(_LI("Add SG-volume attachment, volume_id: %s"), id)
        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)

        params = body['attach']
        params = {} if params is None else params
        instance_uuid = params.get('instance_uuid', None)

        mode = params.get('mode', None)
        if mode is None:
            mode = 'rw'
        if instance_uuid is None:
            msg = _("Invalid request to attach volume to an invalid target")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        if mode not in ('rw', 'ro'):
            msg = _("Invalid request to attach volume to an invalid mode. "
                    "Attaching mode should be 'rw' or 'ro'.")
            raise webob.exc.HTTPBadRequest(explanation=msg)

        attach_result = self.service_api.attach(context, volume, instance_uuid,
                                                mode)
        return self._view_builder.attach_summary(req, attach_result)

    @wsgi.action('detach')
    def detach(self, req, id, body):
        """Clear attachment metadata."""
        LOG.info(_LI("Clear SG-volume attachment with volume_id: %s"), id)
        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)
        params = body['detach']
        params = {} if params is None else params
        instance_uuid = params.get('instance_uuid', None)
        self.service_api.detach(context, volume, instance_uuid)
        return webob.Response(status_int=202)

    @wsgi.action('reset_status')
    def reset_status(self, req, id, body):
        """reset volume status"""
        LOG.info(_LI("Reset volume status, id: %s"), id)
        status = body['reset_status'].get('status',
                                          fields.VolumeStatus.ENABLED)
        if status not in fields.VolumeStatus.ALL:
            msg = _("Invalid status provided.")
            LOG.error(msg)
            raise exception.InvalidStatus(status=status)

        context = req.environ['sgservice.context']
        volume = self.service_api.get(context, id)
        volume.status = status
        volume.save()
        return webob.Response(status_int=202)
Esempio n. 4
0
 def __init__(self):
     self.service_api = ServiceAPI()
     super(VolumesController, self).__init__()
Esempio n. 5
0
class ReplicationsController(wsgi.Controller):
    """The Replications API controller for the SG-Service."""

    _view_builder_class = ReplicationViewBuilder

    def __init__(self):
        self.service_api = ServiceAPI()
        super(ReplicationsController, self).__init__()

    def _get_replication_filter_options(self):
        return CONF.query_replication_filters

    def show(self, req, id):
        """Return data about the given replications."""
        LOG.info(_LI("Show replication with id: %s"), id)
        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        return self._view_builder.detail(req, replication)

    def delete(self, req, id):
        """Delete a replication."""
        LOG.info(_LI("Delete replication with id: %s"), id)
        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        self.service_api.delete_replication(context, replication)
        return webob.Response(status_int=202)

    def index(self, req):
        """Returns a list of replications, transformed through view builder."""
        LOG.info(_LI("Show replication list"))
        context = req.environ['sgservice.context']
        params = req.params.copy()
        marker, limit, offset = common.get_pagination_params(params)
        sort_keys, sort_dirs = common.get_sort_params(params)
        filters = params

        utils.remove_invaild_filter_options(
            context, filters, self._get_replication_filter_options())
        utils.check_filters(filters)

        if 'name' in sort_keys:
            sort_keys[sort_keys.index('name')] = 'display_name'

        if 'name' in filters:
            filters['display_name'] = filters.pop('name')

        replications = self.service_api.get_all_replications(
            context,
            marker=marker,
            limit=limit,
            sort_keys=sort_keys,
            sort_dirs=sort_dirs,
            filters=filters,
            offset=offset)

        retval_replications = self._view_builder.detail_list(req, replications)
        LOG.info(_LI("Show replication list request issued successfully."))
        return retval_replications

    def create(self, req, body):
        """Creates a new replication."""
        if not self.is_valid_body(body, 'replication'):
            raise exc.HTTPUnprocessableEntity()
        LOG.debug('Create replication request body: %s', body)
        context = req.environ['sgservice.context']
        replication = body['replication']

        master_volume_id = replication.get('master_volume', None)
        if master_volume_id is None:
            msg = _('Incorrect request body format')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        slave_volume_id = replication.get('slave_volume', None)
        if slave_volume_id is None:
            msg = _('Incorrect request body format')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        name = replication.get('name', None)
        description = replication.get('description', None)
        if description is None:
            description = 'replication:%s-%s' % (master_volume_id,
                                                 slave_volume_id)

        master_volume = self.service_api.get(context, master_volume_id)
        slave_volume = self.service_api.get(context, slave_volume_id)
        replication = self.service_api.create_replication(
            context, name, description, master_volume, slave_volume)
        return self._view_builder.detail(req, replication)

    def update(self, req, id, body):
        """Update a replication."""
        LOG.info(_LI("Update replication with id: %s"), id)
        context = req.environ['sgservice.context']
        if not body:
            msg = _("Missing request body")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        if 'replication' not in body:
            msg = (_("Missing required element '%s' in request body"),
                   'replication')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        replication = body['replication']
        update_dict = {}

        valid_update_keys = (
            'name',
            'description',
            'display_name',
            'display_description',
        )
        for key in valid_update_keys:
            if key in replication:
                update_dict[key] = replication[key]
        self.validate_name_and_description(update_dict)
        if 'name' in update_dict:
            update_dict['display_name'] = update_dict.pop('name')
        if 'description' in update_dict:
            update_dict['display_description'] = update_dict.pop('description')

        replication = self.service_api.get_replication(context, id)
        replication.update(update_dict)
        replication.save()

        return self._view_builder.detail(req, replication)

    @wsgi.action('enable')
    def enable(self, req, id, body):
        """Enable a disabled-replication"""
        LOG.info(_LI("Enable replication with id: %s"), id)
        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        replication = self.service_api.enable_replication(context, replication)
        return self._view_builder.detail(req, replication)

    @wsgi.action('disable')
    def disable(self, req, id, body):
        """Disable a failed-over replication"""
        LOG.info(_LI("Disable replication with id: %s"), id)
        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        replication = self.service_api.disable_replication(
            context, replication)
        return self._view_builder.detail(req, replication)

    @wsgi.action('failover')
    def failover(self, req, id, body):
        """Failover a enabled replication"""
        LOG.info(_LI("Failover replication with id: %s"), id)
        context = req.environ['sgservice.context']

        params = body['failover']
        force = params.get('force', False)
        replication = self.service_api.get_replication(context, id)
        replication = self.service_api.failover_replication(
            context, replication, force)
        return self._view_builder.detail(req, replication)

    @wsgi.action('reverse')
    def reverse(self, req, id, body):
        """reverse a enabled replication"""
        LOG.info(_LI("Reverse replication with id: %s"), id)
        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        replication = self.service_api.reverse_replication(
            context, replication)
        return self._view_builder.detail(req, replication)

    @wsgi.action('reset_status')
    def reset_status(self, req, id, body):
        """reset replication status"""
        LOG.info(_LI("Reset replication status, id: %s"), id)
        status = body['reset_status'].get('status',
                                          fields.ReplicationStatus.ENABLED)
        if status not in fields.ReplicationStatus.ALL:
            msg = _("Invalid status provided.")
            LOG.error(msg)
            raise exception.InvalidStatus(status=status)

        context = req.environ['sgservice.context']
        replication = self.service_api.get_replication(context, id)
        replication.status = status
        replication.save()
        # reset master volume replicate status
        master_volume = self.service_api.get(context,
                                             replication.master_volume)
        if master_volume.replicate_status not in [
                None, fields.ReplicateStatus.DELETED
        ]:
            master_volume.replicate_status = status
        master_volume.save()

        # reset slave volume replicate status
        slave_volume = self.service_api.get(context, replication.slave_volume)
        if slave_volume.replicate_status not in [
                None, fields.ReplicateStatus.DELETED
        ]:
            slave_volume.replicate_status = status
        slave_volume.save()
        return webob.Response(status_int=202)
Esempio n. 6
0
 def __init__(self):
     self.service_api = ServiceAPI()
     super(ReplicationsController, self).__init__()
Esempio n. 7
0
 def __init__(self):
     self.service_api = ServiceAPI()
     super(CheckpointsController, self).__init__()
Esempio n. 8
0
 def __init__(self):
     self.service_api = ServiceAPI()
     super(BackupsController, self).__init__()
Esempio n. 9
0
class BackupsController(wsgi.Controller):
    """The Backups API controller for the SG-Service."""

    _view_builder_class = BackupViewBuilder

    def __init__(self):
        self.service_api = ServiceAPI()
        super(BackupsController, self).__init__()

    def _get_backup_filter_options(self):
        return CONF.query_backup_filters

    def show(self, req, id):
        """Return data about the given backups."""
        LOG.info(_LI("Show backup, backup_id: %s"), id)
        context = req.environ['sgservice.context']
        backup = self.service_api.get_backup(context, id)
        return self._view_builder.detail(req, backup)

    def delete(self, req, id):
        """Delete a backup."""
        LOG.info(_LI("Delete backup, backup_id: %s"), id)
        context = req.environ['sgservice.context']
        backup = self.service_api.get_backup(context, id)
        self.service_api.delete_backup(context, backup)
        return webob.Response(status_int=202)

    def index(self, req):
        """Returns a list of backups, transformed through view builder."""
        LOG.info(_LI("Show backup list"))
        context = req.environ['sgservice.context']
        params = req.params.copy()
        marker, limit, offset = common.get_pagination_params(params)
        sort_keys, sort_dirs = common.get_sort_params(params)
        filters = params

        utils.remove_invaild_filter_options(context, filters,
                                            self._get_backup_filter_options())
        utils.check_filters(filters)

        if 'name' in sort_keys:
            sort_keys[sort_keys.index('name')] = 'display_name'

        if 'name' in filters:
            filters['display_name'] = filters.pop('name')

        backups = self.service_api.get_all_backups(context,
                                                   marker=marker,
                                                   limit=limit,
                                                   sort_keys=sort_keys,
                                                   sort_dirs=sort_dirs,
                                                   filters=filters,
                                                   offset=offset)

        retval_backups = self._view_builder.detail_list(req, backups)
        LOG.info(_LI("Show backup list request issued successfully."))
        return retval_backups

    def create(self, req, body):
        """Creates a new backup."""
        LOG.debug('Create backup request body: %s', body)
        context = req.environ['sgservice.context']
        backup = body['backup']

        volume_id = backup.get('volume_id', None)
        if volume_id is None:
            msg = _('Incorrect request body format')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        name = backup.get('name', None)
        description = backup.get('description', None)
        if description is None:
            description = 'backup-%s' % volume_id

        backup_type = backup.get('type')
        if backup_type is None:
            backup_type = constants.FULL_BACKUP
        if backup_type not in constants.SUPPORT_BACKUP_TYPES:
            msg = _('backup type should be full or incremental')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        backup_destination = backup.get('destination')
        if backup_destination is None:
            backup_destination = constants.LOCAL_BACKUP
        if backup_destination not in constants.SUPPORT_BACKUP_DESTINATIONS:
            msg = _('backup destination should be local or remote')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        volume = self.service_api.get(context, volume_id)
        backup = self.service_api.create_backup(context, name, description,
                                                volume, backup_type,
                                                backup_destination)
        return self._view_builder.detail(req, backup)

    def update(self, req, id, body):
        """Update a backup."""
        LOG.info(_LI("Update backup, backup_id: %s"), id)
        context = req.environ['sgservice.context']
        if not body:
            msg = _("Missing request body")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        if 'backup' not in body:
            msg = (_("Missing required element '%s' in request body"),
                   'backup')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        backup = body['backup']
        update_dict = {}

        valid_update_keys = (
            'name',
            'description',
            'display_name',
            'display_description',
        )
        for key in valid_update_keys:
            if key in backup:
                update_dict[key] = backup[key]
        self.validate_name_and_description(update_dict)
        if 'name' in update_dict:
            update_dict['display_name'] = update_dict.pop('name')
        if 'description' in update_dict:
            update_dict['display_description'] = update_dict.pop('description')

        backup = self.service_api.get_backup(context, id)
        backup.update(update_dict)
        backup.save()
        return self._view_builder.detail(req, backup)

    @wsgi.action('restore')
    def restore(self, req, id, body):
        """Restore backup to an SG-enabled volume"""
        LOG.info(_LI("Restore backup to sg-enabled volume, backup_id: %s"), id)
        context = req.environ['sgservice.context']
        backup = self.service_api.get_backup(context, id)
        restore = body['restore']
        volume_id = restore.get('volume_id', None)
        if volume_id is None:
            msg = _('restored volume should be specified.')
            raise webob.exc.HTTPBadRequest(explanation=msg)

        restore = self.service_api.restore_backup(context, backup, volume_id)
        return self._view_builder.restore_summary(req, restore)

    @wsgi.action('export_record')
    def export_record(self, req, id, body):
        """Export backup record"""
        LOG.info(_LI("Export backup record, backup_id: %s"), id)
        context = req.environ['sgservice.context']
        backup = self.service_api.get_backup(context, id)

        record = self.service_api.export_record(context, backup)
        return self._view_builder.export_summary(req, record)

    def import_record(self, req, body):
        """Import a backup"""
        LOG.info(_LI("Importing record from body: %s"), body)
        self.assert_valid_body(body, 'backup_record')
        context = req.environ['sgservice.context']
        backup_record = body['backup_record']
        # Verify that body elements are provided
        try:
            driver_data = backup_record['driver_data']
        except KeyError:
            msg = _("Incorrect request body format.")
            raise webob.exc.HTTPBadRequest(explanation=msg)
        LOG.debug('Importing backup using driver_data %s.', driver_data)

        try:
            new_backup = self.service_api.import_record(context, backup_record)
        except exception.InvalidBackup as error:
            raise webob.exc.HTTPBadRequest(explanation=error.msg)
        # Other Not found exceptions will be handled at the wsgi level
        except exception.ServiceNotFound as error:
            raise webob.exc.HTTPInternalServerError(explanation=error.msg)

        retval = self._view_builder.detail(req, new_backup)
        return retval

    @wsgi.action('reset_status')
    def reset_status(self, req, id, body):
        """reset backup status"""
        LOG.info(_LI("Reset backup status, id: %s"), id)
        status = body['reset_status'].get('status',
                                          fields.BackupStatus.AVAILABLE)
        if status not in fields.BackupStatus.ALL:
            msg = _("Invalid status provided.")
            LOG.error(msg)
            raise exception.InvalidStatus(status=status)

        context = req.environ['sgservice.context']
        backup = self.service_api.get_backup(context, id)
        backup.status = status
        backup.save()
        return webob.Response(status_int=202)