1
0
mirror of https://github.com/OpenNebula/one.git synced 2025-02-08 05:57:23 +03:00

Merge remote-tracking branch 'origin/feature-1697'

This commit is contained in:
Carlos Martín 2013-02-18 15:07:40 +01:00
commit b5c31213ee
8 changed files with 128 additions and 15 deletions

View File

@ -57,7 +57,7 @@ public:
VMTemplateInstantiate():
RequestManagerVMTemplate("TemplateInstantiate",
"Instantiates a new virtual machine using a template",
"A:sisb")
"A:sisbs")
{
auth_op = AuthRequest::USE;
};

View File

@ -312,6 +312,17 @@ public:
*/
int from_xml_node(const xmlNodePtr node);
/**
* Merges another Template, adding the new attributes and
* replacing the existing ones
*
* @param from_tmpl the template to be merged
* @param error_str string describing the error
*
* @return 0 on success.
*/
int merge(const Template * from_tmpl, string& error_str);
protected:
/**
* The template attributes

View File

@ -23,7 +23,7 @@ class OneTemplateHelper < OpenNebulaHelper::OneHelper
:format => String,
:description => <<-EOT.strip
Name of the new VM or TEMPLATE. When instantiating
multiple VMs you can use the\"%i\" wildcard to produce
multiple VMs you can use the \"%i\" wildcard to produce
different names such as vm-0, vm-1...
EOT
}

View File

@ -172,10 +172,16 @@ cmd=CommandParser::CmdParser.new(ARGV) do
managed with the 'onevm' command
EOT
command :instantiate, instantiate_desc, :templateid,
:options=>instantiate_options do
command :instantiate, instantiate_desc, :templateid, [:file, nil],
:options=>instantiate_options+OpenNebulaHelper::TEMPLATE_OPTIONS do
exit_code=0
if args[1] && OpenNebulaHelper.create_template_options_used?(options)
STDERR.puts "You cannot use both template file and template"<<
" creation options."
next -1
end
number = options[:multiple] || 1
number.times do |i|
exit_code=helper.perform_action(args[0],options,"instantiated") do |t|
@ -184,7 +190,22 @@ cmd=CommandParser::CmdParser.new(ARGV) do
on_hold = options[:hold] != nil
res = t.instantiate(name, on_hold)
extra_template = ""
if args[1]
extra_template = File.read(args[1])
else
res = OpenNebulaHelper.create_template(options)
if res.first != 0
STDERR.puts res.last
next -1
end
extra_template = res.last
end
res = t.instantiate(name, on_hold, extra_template)
if !OpenNebula.is_error?(res)
puts "VM ID: #{res}"

View File

@ -201,12 +201,14 @@ public class Template extends PoolElement
* @param id The template id of the target template.
* @param name A string containing the name of the VM instance, can be empty.
* @param onHold False to create this VM in pending state, true on hold
* @param template User provided Template to merge with the one
* being instantiated
* @return If successful the message contains the VM Instance ID.
*/
public static OneResponse instantiate(Client client, int id, String name,
boolean onHold)
boolean onHold, String template)
{
return client.call(INSTANTIATE, id, name, onHold);
return client.call(INSTANTIATE, id, name, onHold, template);
}
/**
@ -389,11 +391,13 @@ public class Template extends PoolElement
*
* @param name A string containing the name of the VM instance, can be empty.
* @param onHold False to create this VM in pending state, true on hold
* @param template User provided Template to merge with the one
* being instantiated
* @return If successful the message contains the VM Instance ID.
*/
public OneResponse instantiate(String name, boolean onHold)
public OneResponse instantiate(String name, boolean onHold, String template)
{
return instantiate(client, id, name, onHold);
return instantiate(client, id, name, onHold, template);
}
/**
@ -404,7 +408,7 @@ public class Template extends PoolElement
*/
public OneResponse instantiate(String name)
{
return instantiate(client, id, name, false);
return instantiate(client, id, name, false, "");
}
/**
@ -414,7 +418,7 @@ public class Template extends PoolElement
*/
public OneResponse instantiate()
{
return instantiate(client, id, "", false);
return instantiate(client, id, "", false, "");
}
/**

View File

@ -90,14 +90,19 @@ module OpenNebula
# string OpenNebula will set a default name
# @param hold [true,false] false to create the VM in pending state,
# true to create it on hold
# @param template [String] User provided Template to merge with the
# one being instantiated
#
# @return [Integer, OpenNebula::Error] The new VM id, Error
# otherwise
def instantiate(name="", hold=false)
def instantiate(name="", hold=false, template="")
return Error.new('ID not defined') if !@pe_id
name ||= ""
rc = @client.call(TEMPLATE_METHODS[:instantiate], @pe_id, name, hold)
template ||= ""
rc = @client.call(
TEMPLATE_METHODS[:instantiate], @pe_id, name, hold, template)
return rc
end

View File

@ -27,6 +27,7 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
int id = xmlrpc_c::value_int(paramList.getInt(1));
string name = xmlrpc_c::value_string(paramList.getString(2));
bool on_hold = false; //Optional XML-RPC argument
string str_uattrs; //Optional XML-RPC argument
int rc;
int vid;
@ -43,6 +44,7 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
UserPool * upool = nd.get_upool();
VirtualMachineTemplate * tmpl;
VirtualMachineTemplate uattrs;
VMTemplate * rtmpl;
User * user;
@ -54,6 +56,8 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
if ( paramList.size() > 3 )
{
on_hold = xmlrpc_c::value_boolean(paramList.getBoolean(3));
str_uattrs = xmlrpc_c::value_string(paramList.getString(4));
}
/* ---------------------------------------------------------------------- */
@ -98,8 +102,7 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
rtmpl->unlock();
// Check template for restricted attributes, only if owner is not oneadmin
if ( perms.uid != UserPool::ONEADMIN_ID && perms.gid != GroupPool::ONEADMIN_ID )
if (perms.uid!=UserPool::ONEADMIN_ID && perms.gid!=GroupPool::ONEADMIN_ID)
{
if (tmpl->check(aname))
{
@ -116,6 +119,45 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
}
}
// Parse & merge user attributes (check if the request user is not oneadmin)
if (!str_uattrs.empty())
{
rc = uattrs.parse_str_or_xml(str_uattrs, error_str);
if ( rc != 0 )
{
failure_response(INTERNAL, error_str, att);
delete tmpl;
return;
}
if (att.uid!=UserPool::ONEADMIN_ID && att.gid!=GroupPool::ONEADMIN_ID)
{
if (uattrs.check(aname))
{
ostringstream oss;
oss << "User Template includes a restricted attribute "<< aname;
failure_response(AUTHORIZATION,
authorization_error(oss.str(), att),
att);
delete tmpl;
return;
}
}
rc = tmpl->merge(&uattrs, error_str);
if ( rc != 0 )
{
failure_response(INTERNAL, error_str, att);
delete tmpl;
return;
}
}
/* ---------------------------------------------------------------------- */
/* Store the template attributes in the VM */
/* ---------------------------------------------------------------------- */
@ -139,6 +181,16 @@ void VMTemplateInstantiate::request_execute(xmlrpc_c::paramList const& paramList
ar.add_auth(auth_op, perms); //USE TEMPLATE
if (!str_uattrs.empty())
{
PoolObjectAuth tmp_perms;
perms.uid = att.uid;
perms.obj_type = auth_object;
ar.add_auth(AuthRequest::CREATE, tmp_perms); //CREATE TEMPLATE
}
VirtualMachine::set_auth_request(att.uid, ar, tmpl);
if (UserPool::authorize(ar) == -1)

View File

@ -691,6 +691,26 @@ int Template::from_xml_node(const xmlNodePtr node)
/* ------------------------------------------------------------------------ */
/* ------------------------------------------------------------------------ */
int Template::merge(const Template * from_tmpl, string& error_str)
{
multimap<string,Attribute *>::const_iterator it;
for (it = from_tmpl->attributes.begin(); it != from_tmpl->attributes.end(); ++it)
{
this->erase(it->first);
}
for (it = from_tmpl->attributes.begin(); it != from_tmpl->attributes.end(); ++it)
{
this->set(it->second->clone());
}
return 0;
}
/* ------------------------------------------------------------------------ */
/* ------------------------------------------------------------------------ */
void Template::rebuild_attributes(const xmlNode * root_element)
{
xmlNode * cur_node = 0;