def list_pending_volumes(email, **q_opts): caller_user = _check_authenticated(q_opts) # user must exist user = read_user(email) if user == None: raise Exception("No such user '%s'" % email) # privilege check--only admin can list other users' pending volumes if user.owner_id != caller_user.owner_id and not caller_user.is_admin: raise Exception("User '%s' is not sufficiently privileged" % caller_user.email) def __volume_from_access_request(var): return Volume.Read(var.volume_id, async=True) q_opts["map_func"] = __volume_from_access_request vols = VolumeAccessRequest.ListAll( { "VolumeAccessRequest.requester_owner_id ==": user.owner_id, "VolumeAccessRequest.status ==": VolumeAccessRequest.STATUS_PENDING }, **q_opts) ret = filter(lambda x: x != None, vols) return ret
def list_volume_access(volume_name_or_id, **q_opts): caller_user = _check_authenticated(q_opts) # volume must exist (we need its ID) volume = read_volume(volume_name_or_id) if volume == None or volume.deleted: raise Exception("No such volume '%s'" % volume_name_or_id) if volume.owner_id != caller_user.owner_id and not caller_user.is_admin: raise Exception("User '%s' cannot read Volume '%s'" % (caller_user.email, volume.name)) return VolumeAccessRequest.ListVolumeAccess(volume.volume_id, **q_opts)
def request_volume_access(email, volume_name_or_id, gateway_types, ug_caps, message): user, volume = _read_user_and_volume(email, volume_name_or_id) # defensive checks... if user == None: raise Exception("No such user '%s'" % email) if volume == None or volume.deleted: raise Exception("No such volume '%s'" % volume_name_or_id) return VolumeAccessRequest.RequestAccess(user.owner_id, volume.volume_id, volume.name, gateway_types, ug_caps, message)
def list_volume_user_ids(volume_name_or_id, **q_opts): caller_user = _check_authenticated(q_opts) volume_id = _get_volume_id(volume_name_or_id) def __user_from_access_request(req): return SyndicateUser.Read_ByOwnerID(req.requester_owner_id, async=True) q_opts["map_func"] = __user_from_access_request user_futs = VolumeAccessRequest.ListAll( {"VolumeAccessRequest.volume_id ==": volume_id}, **q_opts) storagetypes.wait_futures(user_futs) ret = [ u.email for u in filter(lambda x: x != None, [uf.get_result() for uf in user_futs]) ] return ret
def remove_volume_access(email, volume_name_or_id, **caller_user_dict): caller_user = _check_authenticated(caller_user_dict) user, volume = _read_user_and_volume(email, volume_name_or_id) # defensive checks... if user == None: raise Exception("No such user '%s'" % email) if volume == None or volume.deleted: raise Exception("No such volume '%s'" % volume_name_or_id) if volume.owner_id == caller_user.owner_id or caller_user.is_admin: # delete the access request...this user cannot create any more gateways return VolumeAccessRequest.RemoveAccessRequest(user.owner_id, volume.volume_id) else: # can't delete raise Exception( "User '%s' is insufficiently privileged to alter access rights for User '%s' in Volume '%s'" % (caller_user.email, user.email, volume.name))
def remove_user_from_volume(email, volume_name_or_id): # NOTE: it's assumed that the caller has done the appropriate authentication. user, volume = _read_user_and_volume(email, volume_name_or_id) # user and volume must exist if user is None: raise Exception("No such user '%s'" % email) if volume is None or volume.deleted: raise Exception("No such Volume '%s'" % email) # delete the volume access request rc = VolumeAccessRequest.RemoveAccessRequest(user.owner_id, volume.volume_id) assert rc is True, "Failed to remove access request for %s in %s" % ( email, volume.name) storagetypes.deferred.defer(_remove_user_from_volume_helper, user.owner_id, volume.volume_id) return True
def set_volume_access(email, volume_name_or_id, allowed_gateways, ug_caps, **caller_user_dict): caller_user = _check_authenticated(caller_user_dict) user, volume = _read_user_and_volume(email, volume_name_or_id) if user is None: # defensive check raise Exception("No such user '%s'" % email) if volume is None or volume.deleted: # defensive check raise Exception("No such Volume '%s'" % volume_name_or_id) # caller user must be admin, or must own the volume if not caller_user.is_admin and volume.owner_id != caller_user.owner_id: raise Exception("User '%s' cannot set access rights to Volume '%s'" % (caller_user.email, volume.name)) return VolumeAccessRequest.GrantAccess(user.owner_id, volume.volume_id, volume.name, allowed_gateways=allowed_gateways, gateway_caps=ug_caps)
def create_gateway(volume_id, email, gateway_type, gateway_name, host, port, **kwargs): if "encryption_password" in kwargs.keys(): del kwargs['encryption_password'] # verify gateway type... if gateway_type not in [GATEWAY_TYPE_UG, GATEWAY_TYPE_RG, GATEWAY_TYPE_AG]: raise Exception("Unrecognized Gateway type %s" % gateway_type) gateway_type_str = GATEWAY_TYPE_TO_STR[gateway_type] caller_user = _check_authenticated(kwargs) # user and volume must both exist user, volume = _read_user_and_volume(email, volume_id) if user == None: raise Exception("No such user '%s'" % email) if (volume == None or volume.deleted): raise Exception("No such volume '%s'" % volume_id) # if the caller user doesn't own this Volume (or isn't an admin), (s)he must have a valid access request if not caller_user.is_admin and caller_user.owner_id != volume.owner_id: # caller user must be the same as the user if caller_user.owner_id != user.owner_id: raise Exception("Caller can only create gateways for itself.") # if the volume is not public, then there needs to be a volume access request that is granted to this user. if not volume.private: # check access status access_request = VolumeAccessRequest.GetAccess( user.owner_id, volume.volume_id) if access_request == None: # user has not been given permission to access this volume raise Exception( "User '%s' is not allowed to access Volume '%s'" % (caller_user.email, volume.name)) if access_request.status != VolumeAccessRequest.STATUS_GRANTED: # user has not been given permission to create a gateway here raise Exception( "User '%s' is not allowed to create a Gateway in Volume '%s'" % (caller_user.email, volume.name)) else: # verify caps requested_caps = kwargs.get("caps", None) if requested_caps is not None and requested_caps != access_request.gateway_caps: raise Exception( "User '%s' is not allowed to set Gateway capabilities '%s'" % requested_caps) # verify the caller is allowed to create this kind of gateway if not access_request.is_gateway_type_allowed(gateway_type): raise Exception( "User '%s' is not allowed to create %s Gateways" % (gateway_type_str)) # user is allowed to create this gateway in this Volume... # verify quota gateway_quota = user.get_gateway_quota(gateway_type) if gateway_quota == 0: gateway_type_str = GATEWAY_TYPE_TO_STR[gateway_type] raise Exception("User '%s' cannot own %s Gateways" % (email, gateway_type_str)) if gateway_quota > 0: gateway_ids = list_gateways_by_user(user.email, caller_user=user, keys_only=True) if len(gateway_ids) > gateway_quota: gateway_type_str = GATEWAY_TYPE_TO_STR[gateway_type] raise Exception( "User '%s' has exceeded quota (%s) for %s Gateways" % (email, gateway_quota, gateway_type_str)) gateway_key = Gateway.Create(user, volume, gateway_type=gateway_type, name=gateway_name, host=host, port=port, **kwargs) gw = gateway_key.get() # reversion volume cert? if gw is not None: storagetypes.deferred.defer(Volume.Reversion, volume_id) return gw
def list_user_access_requests(email, **q_opts): user = read_user(email) if user == None: raise Exception("No such user '%s'" % email) return VolumeAccessRequest.ListUserAccessRequests(user.owner_id, **q_opts)