mirror of
https://github.com/OpenNebula/one.git
synced 2025-03-22 18:50:08 +03:00
Feature #4317: Add option for template delete and chmod to be recursive
This commit is contained in:
parent
91ee796cb6
commit
91b1cc7396
@ -256,6 +256,15 @@ protected:
|
||||
*/
|
||||
void failure_response(ErrorCode ec, RequestAttributes& ra);
|
||||
|
||||
/**
|
||||
* Builds an error response. A descriptive error message
|
||||
* is constructed using att.resp_obj, att.resp_id and/or att.resp_msg and
|
||||
* the ErrorCode
|
||||
* @param ec error code for this call
|
||||
* @param att the specific request attributes
|
||||
*/
|
||||
string failure_message(ErrorCode ec, RequestAttributes& att);
|
||||
|
||||
/* ---------------------------------------------------------------------- */
|
||||
/* Authorization methods for requests */
|
||||
/* ---------------------------------------------------------------------- */
|
||||
|
@ -33,12 +33,30 @@ protected:
|
||||
const string& help)
|
||||
:Request(method_name, "A:siiiiiiiiii", help){};
|
||||
|
||||
RequestManagerChmod(const string& method_name,
|
||||
const string& params,
|
||||
const string& help)
|
||||
:Request(method_name, params, help){};
|
||||
|
||||
~RequestManagerChmod(){};
|
||||
|
||||
/* -------------------------------------------------------------------- */
|
||||
|
||||
virtual void request_execute(xmlrpc_c::paramList const& _paramList,
|
||||
RequestAttributes& att);
|
||||
|
||||
static ErrorCode chmod( PoolSQL * pool,
|
||||
int oid,
|
||||
int owner_u,
|
||||
int owner_m,
|
||||
int owner_a,
|
||||
int group_u,
|
||||
int group_m,
|
||||
int group_a,
|
||||
int other_u,
|
||||
int other_m,
|
||||
int other_a,
|
||||
RequestAttributes& att);
|
||||
};
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
@ -67,6 +85,7 @@ class TemplateChmod : public RequestManagerChmod
|
||||
public:
|
||||
TemplateChmod():
|
||||
RequestManagerChmod("TemplateChmod",
|
||||
"A:siiiiiiiiiib"
|
||||
"Changes permission bits of a virtual machine template")
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
@ -75,6 +94,9 @@ public:
|
||||
};
|
||||
|
||||
~TemplateChmod(){};
|
||||
|
||||
void request_execute(xmlrpc_c::paramList const& _paramList,
|
||||
RequestAttributes& att);
|
||||
};
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
@ -113,6 +135,17 @@ public:
|
||||
|
||||
~ImageChmod(){};
|
||||
|
||||
static ErrorCode chmod( int oid,
|
||||
int owner_u,
|
||||
int owner_m,
|
||||
int owner_a,
|
||||
int group_u,
|
||||
int group_m,
|
||||
int group_a,
|
||||
int other_u,
|
||||
int other_m,
|
||||
int other_a,
|
||||
RequestAttributes& att);
|
||||
};
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
@ -30,6 +30,18 @@ using namespace std;
|
||||
class RequestManagerDelete: public Request
|
||||
{
|
||||
protected:
|
||||
RequestManagerDelete(const string& method_name,
|
||||
const string& params,
|
||||
const string& help)
|
||||
:Request(method_name, params, help)
|
||||
{
|
||||
auth_op = AuthRequest::MANAGE;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
clpool = nd.get_clpool();
|
||||
aclm = nd.get_aclm();
|
||||
};
|
||||
|
||||
RequestManagerDelete(const string& method_name,
|
||||
const string& help)
|
||||
:Request(method_name, "A:si", help)
|
||||
@ -45,11 +57,14 @@ protected:
|
||||
|
||||
/* -------------------------------------------------------------------- */
|
||||
|
||||
void request_execute(xmlrpc_c::paramList const& _paramList,
|
||||
void request_execute(xmlrpc_c::paramList const& paramList,
|
||||
RequestAttributes& att);
|
||||
|
||||
bool delete_authorization(int oid,
|
||||
RequestAttributes& att);
|
||||
static ErrorCode delete_authorization(
|
||||
PoolSQL* pool,
|
||||
int oid,
|
||||
AuthRequest::Operation auth_op,
|
||||
RequestAttributes& att);
|
||||
|
||||
/* -------------------------------------------------------------------- */
|
||||
|
||||
@ -79,6 +94,7 @@ class TemplateDelete : public RequestManagerDelete
|
||||
public:
|
||||
TemplateDelete():
|
||||
RequestManagerDelete("TemplateDelete",
|
||||
"A:sib"
|
||||
"Deletes a virtual machine template")
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
@ -87,6 +103,9 @@ public:
|
||||
};
|
||||
|
||||
~TemplateDelete(){};
|
||||
|
||||
void request_execute(
|
||||
xmlrpc_c::paramList const& paramList, RequestAttributes& att);
|
||||
};
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
@ -137,7 +156,10 @@ public:
|
||||
|
||||
~ImageDelete(){};
|
||||
|
||||
int drop(int oid, PoolObjectSQL * object, string& error_msg);
|
||||
void request_execute(
|
||||
xmlrpc_c::paramList const& paramList, RequestAttributes& att);
|
||||
|
||||
static ErrorCode delete_img(int oid, RequestAttributes& att);
|
||||
};
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
@ -70,6 +70,13 @@ public:
|
||||
*(static_cast<VirtualMachineTemplate *>(obj_template)));
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns all the DISK/IMAGE_IDs in the Template
|
||||
* @return image IDs
|
||||
*/
|
||||
vector<int> get_img_ids();
|
||||
// TODO: make const
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// Virtual Router
|
||||
// ------------------------------------------------------------------------
|
||||
|
@ -585,7 +585,7 @@ void Request::failure_response(ErrorCode ec, const string& str_val,
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
void Request::failure_response(ErrorCode ec, RequestAttributes& att)
|
||||
string Request::failure_message(ErrorCode ec, RequestAttributes& att)
|
||||
{
|
||||
std::ostringstream oss;
|
||||
std::string obname;
|
||||
@ -604,7 +604,7 @@ void Request::failure_response(ErrorCode ec, RequestAttributes& att)
|
||||
switch(ec)
|
||||
{
|
||||
case SUCCESS:
|
||||
return;
|
||||
return "";
|
||||
|
||||
case AUTHORIZATION:
|
||||
oss << "User [" << att.uid << "] ";
|
||||
@ -652,7 +652,15 @@ void Request::failure_response(ErrorCode ec, RequestAttributes& att)
|
||||
break;
|
||||
}
|
||||
|
||||
failure_response(ec, oss.str(), att);
|
||||
return oss.str();
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
void Request::failure_response(ErrorCode ec, RequestAttributes& att)
|
||||
{
|
||||
failure_response(ec, failure_message(ec, att), att);
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
@ -16,7 +16,6 @@
|
||||
|
||||
#include "RequestManagerChmod.h"
|
||||
|
||||
#include "NebulaLog.h"
|
||||
#include "Nebula.h"
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
@ -39,6 +38,39 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
int other_m = xmlrpc_c::value_int(paramList.getInt(9));
|
||||
int other_a = xmlrpc_c::value_int(paramList.getInt(10));
|
||||
|
||||
ErrorCode ec = chmod(pool, oid,
|
||||
owner_u, owner_m, owner_a,
|
||||
group_u, group_m, group_a,
|
||||
other_u, other_m, other_a,
|
||||
att);
|
||||
|
||||
if ( ec == SUCCESS )
|
||||
{
|
||||
success_response(oid, att);
|
||||
}
|
||||
else
|
||||
{
|
||||
failure_response(ec, att);
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
Request::ErrorCode RequestManagerChmod::chmod(
|
||||
PoolSQL * pool,
|
||||
int oid,
|
||||
int owner_u,
|
||||
int owner_m,
|
||||
int owner_a,
|
||||
int group_u,
|
||||
int group_m,
|
||||
int group_a,
|
||||
int other_u,
|
||||
int other_m,
|
||||
int other_a,
|
||||
RequestAttributes& att)
|
||||
{
|
||||
PoolObjectSQL * object;
|
||||
|
||||
if ( att.uid != 0 && att.gid != 0)
|
||||
@ -51,8 +83,7 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
if ( object == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
failure_response(NO_EXISTS, att);
|
||||
return;
|
||||
return NO_EXISTS;
|
||||
}
|
||||
|
||||
object->get_permissions(perms);
|
||||
@ -99,8 +130,7 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
if ( !enable_other )
|
||||
{
|
||||
att.resp_msg = "'other' permissions is disabled in oned.conf";
|
||||
failure_response(AUTHORIZATION, att);
|
||||
return;
|
||||
return AUTHORIZATION;
|
||||
}
|
||||
}
|
||||
|
||||
@ -111,9 +141,7 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
if (UserPool::authorize(ar) == -1)
|
||||
{
|
||||
att.resp_msg = ar.message;
|
||||
failure_response(AUTHORIZATION, att);
|
||||
|
||||
return;
|
||||
return AUTHORIZATION;
|
||||
}
|
||||
}
|
||||
|
||||
@ -124,8 +152,7 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
if ( object == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
failure_response(NO_EXISTS, att);
|
||||
return;
|
||||
return NO_EXISTS;
|
||||
}
|
||||
|
||||
int rc = object->set_permissions(owner_u, owner_m, owner_a, group_u,
|
||||
@ -133,20 +160,114 @@ void RequestManagerChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
failure_response(INTERNAL, att);
|
||||
|
||||
object->unlock();
|
||||
return;
|
||||
return INTERNAL;
|
||||
}
|
||||
|
||||
pool->update(object);
|
||||
|
||||
object->unlock();
|
||||
|
||||
success_response(oid, att);
|
||||
|
||||
return;
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
void TemplateChmod::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
RequestAttributes& att)
|
||||
{
|
||||
int oid = xmlrpc_c::value_int(paramList.getInt(1));
|
||||
|
||||
int owner_u = xmlrpc_c::value_int(paramList.getInt(2));
|
||||
int owner_m = xmlrpc_c::value_int(paramList.getInt(3));
|
||||
int owner_a = xmlrpc_c::value_int(paramList.getInt(4));
|
||||
|
||||
int group_u = xmlrpc_c::value_int(paramList.getInt(5));
|
||||
int group_m = xmlrpc_c::value_int(paramList.getInt(6));
|
||||
int group_a = xmlrpc_c::value_int(paramList.getInt(7));
|
||||
|
||||
int other_u = xmlrpc_c::value_int(paramList.getInt(8));
|
||||
int other_m = xmlrpc_c::value_int(paramList.getInt(9));
|
||||
int other_a = xmlrpc_c::value_int(paramList.getInt(10));
|
||||
|
||||
bool recursive = false;
|
||||
|
||||
if (paramList.size() > 11)
|
||||
{
|
||||
recursive = xmlrpc_c::value_boolean(paramList.getBoolean(11));
|
||||
}
|
||||
|
||||
ErrorCode ec = chmod(pool, oid,
|
||||
owner_u, owner_m, owner_a,
|
||||
group_u, group_m, group_a,
|
||||
other_u, other_m, other_a,
|
||||
att);
|
||||
|
||||
if ( ec != SUCCESS )
|
||||
{
|
||||
failure_response(ec, att);
|
||||
return;
|
||||
}
|
||||
|
||||
if (recursive)
|
||||
{
|
||||
VMTemplate* tmpl = static_cast<VMTemplatePool*>(pool)->get(oid, true);
|
||||
|
||||
if ( tmpl == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
failure_response(NO_EXISTS, att);
|
||||
return;
|
||||
}
|
||||
|
||||
vector<int> img_ids = tmpl->get_img_ids();
|
||||
|
||||
tmpl->unlock();
|
||||
|
||||
ErrorCode ec;
|
||||
|
||||
for (vector<int>::iterator it = img_ids.begin(); it != img_ids.end(); it++)
|
||||
{
|
||||
ec = ImageChmod::chmod(*it,
|
||||
owner_u, owner_m, owner_a,
|
||||
group_u, group_m, group_a,
|
||||
other_u, other_m, other_a,
|
||||
att);
|
||||
|
||||
if (ec != SUCCESS)
|
||||
{
|
||||
NebulaLog::log("ReM", Log::ERROR, failure_message(ec, att));
|
||||
}
|
||||
|
||||
// TODO rollback?
|
||||
}
|
||||
}
|
||||
|
||||
success_response(oid, att);
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
Request::ErrorCode ImageChmod::chmod(
|
||||
int oid,
|
||||
int owner_u,
|
||||
int owner_m,
|
||||
int owner_a,
|
||||
int group_u,
|
||||
int group_m,
|
||||
int group_a,
|
||||
int other_u,
|
||||
int other_m,
|
||||
int other_a,
|
||||
RequestAttributes& att)
|
||||
{
|
||||
return RequestManagerChmod::chmod(
|
||||
Nebula::instance().get_ipool(),
|
||||
oid,
|
||||
owner_u, owner_m, owner_a,
|
||||
group_u, group_m, group_a,
|
||||
other_u, other_m, other_a,
|
||||
att);
|
||||
}
|
||||
|
@ -21,25 +21,26 @@ using namespace std;
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
bool RequestManagerDelete::delete_authorization(
|
||||
int oid,
|
||||
RequestAttributes& att)
|
||||
Request::ErrorCode RequestManagerDelete::delete_authorization(
|
||||
PoolSQL* pool,
|
||||
int oid,
|
||||
AuthRequest::Operation auth_op,
|
||||
RequestAttributes& att)
|
||||
{
|
||||
PoolObjectSQL * object;
|
||||
PoolObjectAuth perms;
|
||||
|
||||
if ( att.uid == 0 )
|
||||
{
|
||||
return true;
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
object = pool->get(oid,true);
|
||||
object = pool->get(oid, true);
|
||||
|
||||
if ( object == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
failure_response(NO_EXISTS, att);
|
||||
return false;
|
||||
return NO_EXISTS;
|
||||
}
|
||||
|
||||
object->get_permissions(perms);
|
||||
@ -53,12 +54,10 @@ bool RequestManagerDelete::delete_authorization(
|
||||
if (UserPool::authorize(ar) == -1)
|
||||
{
|
||||
att.resp_msg = ar.message;
|
||||
failure_response(AUTHORIZATION, att);
|
||||
|
||||
return false;
|
||||
return AUTHORIZATION;
|
||||
}
|
||||
|
||||
return true;
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
@ -70,9 +69,13 @@ void RequestManagerDelete::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
int oid = xmlrpc_c::value_int(paramList.getInt(1));
|
||||
PoolObjectSQL * object;
|
||||
string error_msg;
|
||||
ErrorCode ec;
|
||||
|
||||
if ( delete_authorization(oid, att) == false )
|
||||
ec = delete_authorization(pool, oid, auth_op, att);
|
||||
|
||||
if ( ec != SUCCESS )
|
||||
{
|
||||
failure_response(ec, att);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -141,6 +144,81 @@ int RequestManagerDelete::drop(
|
||||
/* ------------------------------------------------------------------------- */
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
||||
void TemplateDelete::request_execute(
|
||||
xmlrpc_c::paramList const& paramList, RequestAttributes& att)
|
||||
{
|
||||
int oid = xmlrpc_c::value_int(paramList.getInt(1));
|
||||
bool recursive = false;
|
||||
VMTemplate * object;
|
||||
string error_msg;
|
||||
vector<int> img_ids;
|
||||
ErrorCode ec;
|
||||
|
||||
if (paramList.size() > 2)
|
||||
{
|
||||
recursive = xmlrpc_c::value_boolean(paramList.getBoolean(2));
|
||||
}
|
||||
|
||||
ec = delete_authorization(pool, oid, auth_op, att);
|
||||
|
||||
if ( ec != SUCCESS )
|
||||
{
|
||||
failure_response(ec, att);
|
||||
return;
|
||||
}
|
||||
|
||||
object = static_cast<VMTemplatePool*>(pool)->get(oid, true);
|
||||
|
||||
if ( object == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
failure_response(NO_EXISTS, att);
|
||||
return;
|
||||
}
|
||||
|
||||
int rc = pool->drop(object, error_msg);
|
||||
|
||||
if (recursive)
|
||||
{
|
||||
img_ids = object->get_img_ids();
|
||||
}
|
||||
|
||||
object->unlock();
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
att.resp_msg = "Cannot delete " + object_name(auth_object) + ". " + error_msg;
|
||||
failure_response(ACTION, att);
|
||||
return;
|
||||
}
|
||||
|
||||
aclm->del_resource_rules(oid, auth_object);
|
||||
|
||||
if (recursive)
|
||||
{
|
||||
ErrorCode ec;
|
||||
|
||||
for (vector<int>::iterator it = img_ids.begin(); it != img_ids.end(); it++)
|
||||
{
|
||||
ec = ImageDelete::delete_img(*it, att);
|
||||
|
||||
if (ec != SUCCESS)
|
||||
{
|
||||
NebulaLog::log("ReM", Log::ERROR, failure_message(ec, att));
|
||||
}
|
||||
|
||||
// TODO rollback?
|
||||
}
|
||||
}
|
||||
|
||||
success_response(oid, att);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
||||
int HostDelete::drop(int oid, PoolObjectSQL * object, string& error_msg)
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
@ -174,14 +252,66 @@ int HostDelete::drop(int oid, PoolObjectSQL * object, string& error_msg)
|
||||
/* ------------------------------------------------------------------------- */
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
||||
int ImageDelete::drop(int oid, PoolObjectSQL * object, string& error_msg)
|
||||
void ImageDelete::request_execute(
|
||||
xmlrpc_c::paramList const& paramList, RequestAttributes& att)
|
||||
{
|
||||
int oid = xmlrpc_c::value_int(paramList.getInt(1));
|
||||
|
||||
ErrorCode ec = delete_img(oid, att);
|
||||
|
||||
if ( ec == SUCCESS )
|
||||
{
|
||||
success_response(oid, att);
|
||||
}
|
||||
else
|
||||
{
|
||||
failure_response(ec, att);
|
||||
}
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
||||
Request::ErrorCode ImageDelete::delete_img(int oid, RequestAttributes& att)
|
||||
{
|
||||
Image * object;
|
||||
string error_msg;
|
||||
ErrorCode ec;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
ImageManager * imagem = nd.get_imagem();
|
||||
AclManager * aclm = nd.get_aclm();
|
||||
ImagePool * pool = nd.get_ipool();
|
||||
|
||||
object->unlock();
|
||||
PoolObjectSQL::ObjectType auth_object = PoolObjectSQL::IMAGE;
|
||||
|
||||
return imagem->delete_image(oid, error_msg);
|
||||
ec = delete_authorization(pool, oid, AuthRequest::MANAGE, att);
|
||||
|
||||
if ( ec != SUCCESS )
|
||||
{
|
||||
att.resp_obj = auth_object;
|
||||
return ec;
|
||||
}
|
||||
|
||||
object = pool->get(oid, false);
|
||||
|
||||
if ( object == 0 )
|
||||
{
|
||||
att.resp_id = oid;
|
||||
return NO_EXISTS;
|
||||
}
|
||||
|
||||
int rc = imagem->delete_image(oid, error_msg);
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
att.resp_msg = "Cannot delete " + object_name(auth_object) + ". " + error_msg;
|
||||
return ACTION;
|
||||
}
|
||||
|
||||
aclm->del_resource_rules(oid, auth_object);
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
@ -257,3 +257,34 @@ bool VMTemplate::is_vrouter()
|
||||
|
||||
return vr;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------ */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
|
||||
vector<int> VMTemplate::get_img_ids()
|
||||
{
|
||||
vector<int> img_ids;
|
||||
|
||||
// TODO: xpaths(vector<int>..) is not working
|
||||
//xpaths(img_ids,"/VMTEMPLATE/TEMPLATE/DISK/IMAGE_ID");
|
||||
|
||||
vector<string> img_ids_st;
|
||||
vector<string>::iterator it;
|
||||
|
||||
xpaths(img_ids_st,"/VMTEMPLATE/TEMPLATE/DISK/IMAGE_ID");
|
||||
|
||||
for (it = img_ids_st.begin(); it != img_ids_st.end(); it++)
|
||||
{
|
||||
istringstream iss(*it);
|
||||
int val;
|
||||
|
||||
iss >> dec >> val;
|
||||
|
||||
if (!iss.fail())
|
||||
{
|
||||
img_ids.push_back( val );
|
||||
}
|
||||
}
|
||||
|
||||
return img_ids;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user