mirror of
https://github.com/OpenNebula/one.git
synced 2025-03-26 06:50:09 +03:00
feature #1696: Clone now supports a target datastore for images
This commit is contained in:
parent
752888b043
commit
3fb497730d
@ -114,6 +114,15 @@ public:
|
||||
return tm_mad;
|
||||
};
|
||||
|
||||
/**
|
||||
* Retrieves DS mad name
|
||||
* @return string ds mad name
|
||||
*/
|
||||
const string& get_ds_mad() const
|
||||
{
|
||||
return ds_mad;
|
||||
};
|
||||
|
||||
/**
|
||||
* Retrieves the base path
|
||||
* @return base path string
|
||||
|
@ -161,9 +161,11 @@ cmd=CommandParser::CmdParser.new(ARGV) do
|
||||
Creates a new Image from an existing one
|
||||
EOT
|
||||
|
||||
command :clone, clone_desc, :imageid, :name do
|
||||
command :clone, clone_desc, :imageid, :name,
|
||||
:options=>[OneDatastoreHelper::DATASTORE] do
|
||||
helper.perform_action(args[0],options,"cloned") do |image|
|
||||
res = image.clone(args[1])
|
||||
ds_id = options[:datastore] || -1 # -1 clones to self
|
||||
res = image.clone(args[1], ds_id)
|
||||
|
||||
if !OpenNebula.is_error?(res)
|
||||
puts "ID: #{res}"
|
||||
|
@ -206,10 +206,10 @@ module OpenNebula
|
||||
#
|
||||
# @return [Integer, OpenNebula::Error] The new Image ID in case
|
||||
# of success, Error otherwise
|
||||
def clone(name)
|
||||
def clone(name, target_ds=-1)
|
||||
return Error.new('ID not defined') if !@pe_id
|
||||
|
||||
rc = @client.call(IMAGE_METHODS[:clone], @pe_id, name)
|
||||
rc = @client.call(IMAGE_METHODS[:clone], @pe_id, name, target_ds)
|
||||
|
||||
return rc
|
||||
end
|
||||
|
@ -230,12 +230,12 @@ void ImageClone::request_execute(
|
||||
string name = xmlrpc_c::value_string(paramList.getString(2));
|
||||
|
||||
long long avail, size;
|
||||
int rc, new_id, ds_id;
|
||||
string error_str, ds_name, ds_data;
|
||||
int rc, new_id, ds_id_orig, ds_id = -1;
|
||||
string error_str, ds_name, ds_data, ds_mad;
|
||||
bool ds_check;
|
||||
|
||||
Image::DiskType disk_type;
|
||||
PoolObjectAuth perms, ds_perms;
|
||||
PoolObjectAuth perms, ds_perms, ds_perms_orig;
|
||||
|
||||
ImageTemplate * tmpl;
|
||||
Template img_usage;
|
||||
@ -247,6 +247,11 @@ void ImageClone::request_execute(
|
||||
DatastorePool * dspool = nd.get_dspool();
|
||||
ImagePool * ipool = static_cast<ImagePool *>(pool);
|
||||
|
||||
if (paramList.size() > 3)
|
||||
{
|
||||
ds_id = xmlrpc_c::value_int(paramList.getInt(3));
|
||||
}
|
||||
|
||||
// ------------------------- Get source Image info -------------------------
|
||||
|
||||
img = ipool->get(clone_id, true);
|
||||
@ -281,13 +286,18 @@ void ImageClone::request_execute(
|
||||
|
||||
img->get_permissions(perms);
|
||||
|
||||
ds_id = img->get_ds_id();
|
||||
ds_name = img->get_ds_name();
|
||||
size = img->get_size();
|
||||
if (ds_id == -1) //Target Datastore not set, use the current one
|
||||
{
|
||||
ds_id = img->get_ds_id();
|
||||
}
|
||||
|
||||
ds_id_orig = img->get_ds_id();
|
||||
|
||||
size = img->get_size();
|
||||
|
||||
img->unlock();
|
||||
|
||||
// ------------------------- Get Datastore info ----------------------------
|
||||
// ----------------------- Get target Datastore info -----------------------
|
||||
|
||||
ds = dspool->get(ds_id, true);
|
||||
|
||||
@ -301,15 +311,14 @@ void ImageClone::request_execute(
|
||||
return;
|
||||
}
|
||||
|
||||
if ( ds->get_type() == Datastore::FILE_DS )
|
||||
if ( ds->get_type() != Datastore::IMAGE_DS )
|
||||
{
|
||||
failure_response(ACTION, "Clone not supported for FILE_DS Datastores",
|
||||
att);
|
||||
|
||||
delete tmpl;
|
||||
failure_response(ACTION,
|
||||
request_error("Clone only supported for IMAGE_DS Datastores",""),att);
|
||||
|
||||
ds->unlock();
|
||||
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
@ -320,9 +329,51 @@ void ImageClone::request_execute(
|
||||
ds->to_xml(ds_data);
|
||||
|
||||
ds_check = ds->get_avail_mb(avail);
|
||||
ds_name = ds->get_name();
|
||||
ds_mad = ds->get_ds_mad();
|
||||
|
||||
ds->unlock();
|
||||
|
||||
if (ds_id != ds_id_orig) //check same DS_MAD
|
||||
{
|
||||
ds = dspool->get(ds_id_orig, true);
|
||||
|
||||
if (ds == 0)
|
||||
{
|
||||
failure_response(NO_EXISTS,
|
||||
get_error(object_name(PoolObjectSQL::DATASTORE),ds_id_orig),att);
|
||||
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
if (ds->get_type() != Datastore::IMAGE_DS)
|
||||
{
|
||||
failure_response(ACTION, request_error(
|
||||
"Clone only supported for IMAGE_DS Datastores",""), att);
|
||||
|
||||
ds->unlock();
|
||||
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
if (ds->get_ds_mad() != ds_mad)
|
||||
{
|
||||
failure_response(ACTION, request_error(
|
||||
"Clone only supported to same DS_MAD Datastores",""), att);
|
||||
|
||||
ds->unlock();
|
||||
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
ds->get_permissions(ds_perms_orig);
|
||||
|
||||
ds->unlock();
|
||||
}
|
||||
|
||||
// ------------- Set authorization request ---------------------------------
|
||||
|
||||
img_usage.add("DATASTORE", ds_id);
|
||||
@ -330,7 +381,8 @@ void ImageClone::request_execute(
|
||||
|
||||
if (ds_check && (size > avail))
|
||||
{
|
||||
failure_response(ACTION, "Not enough space in datastore", att);
|
||||
failure_response(ACTION,
|
||||
request_error("Not enough space in datastore",""), att);
|
||||
|
||||
delete tmpl;
|
||||
return;
|
||||
@ -349,6 +401,11 @@ void ImageClone::request_execute(
|
||||
|
||||
ar.add_auth(AuthRequest::USE, ds_perms); // USE DATASTORE
|
||||
|
||||
if (ds_id != ds_id_orig) // USE (original) DATASTORE
|
||||
{
|
||||
ar.add_auth(AuthRequest::USE, ds_perms_orig); // USE DATASTORE
|
||||
}
|
||||
|
||||
if (UserPool::authorize(ar) == -1)
|
||||
{
|
||||
failure_response(AUTHORIZATION,
|
||||
|
Loading…
x
Reference in New Issue
Block a user