def post(self, account, rse): """ --- summary: Create or update a local accont limit tags: - Account Limit parameters: - name: account in: path description: The account for the accountlimit. schema: type: string style: simple - name: rse in: path description: The rse for the accountlimit. schema: type: string style: simple requestBody: content: 'application/json': schema: type: object required: - bytes properties: bytes: description: The new limit in bytes. type: integer responses: 201: description: OK content: application/json: schema: type: string enum: ['Created'] 401: description: Invalid Auth Token 404: description: No RSE or account found for the given id. """ parameters = json_parameters() bytes_param = param_get(parameters, 'bytes') try: set_local_account_limit(account=account, rse=rse, bytes_=bytes_param, issuer=request.environ.get('issuer'), vo=request.environ.get('vo')) except AccessDenied as error: return generate_http_error_flask(401, error) except (RSENotFound, AccountNotFound) as error: return generate_http_error_flask(404, error) return 'Created', 201
def test_api_subscription(self): """ SUBSCRIPTION (API): Test external representation of subscriptions """ sub = 'ext_' + generate_uuid() did = 'ext_' + generate_uuid() new_acc_name = ''.join(random.choice(string.ascii_lowercase) for x in range(10)) new_scope_name = ''.join(random.choice(string.ascii_lowercase) for x in range(10)) add_account(new_acc_name, 'USER', '*****@*****.**', 'root', **self.new_vo) add_scope(new_scope_name, new_acc_name, 'root', **self.new_vo) api_acc_lim.set_local_account_limit(new_acc_name, self.rse3_name, 10, 'root', **self.new_vo) api_acc_lim.set_local_account_limit(new_acc_name, self.rse4_name, 10, 'root', **self.new_vo) add_did(new_scope_name, did, 'DATASET', 'root', account=new_acc_name, rse=self.rse3_name, **self.new_vo) sub_id = add_subscription(sub, new_acc_name, {'account': [new_acc_name], 'scope': [new_scope_name]}, [{'copies': 1, 'rse_expression': self.rse3_name, 'weight': 0, 'activity': 'User Subscriptions', 'source_replica_expression': self.rse4_name}], '', False, 0, 0, 3, 'root', **self.new_vo) add_replication_rule(dids=[{'scope': new_scope_name, 'name': did}], copies=1, rse_expression=self.rse3_name, weight=None, lifetime=180, grouping='DATASET', account=new_acc_name, locked=False, subscription_id=sub_id, source_replica_expression=self.rse4_name, activity='User Subscriptions', notify=None, purge_replicas=False, ignore_availability=False, comment='', ask_approval=False, asynchronous=False, priority=0, split_container=False, meta='', issuer='root', **self.new_vo) out = list_subscriptions(sub, **self.new_vo) out = list(out) assert_not_equal(0, len(out)) assert_in(sub_id, [o['id'] for o in out]) for o in out: if o['id'] == sub_id: assert_equal(o['account'], new_acc_name) rules = loads(o['replication_rules'])[0] assert_equal(rules['rse_expression'], self.rse3_name) assert_equal(rules['source_replica_expression'], self.rse4_name) fil = loads(o['filter']) assert_equal(fil['account'], [new_acc_name]) assert_equal(fil['scope'], [new_scope_name]) out = list_subscription_rule_states(sub, **self.new_vo) out = list(out) assert_not_equal(0, len(out)) for o in out: assert_equal(o.account, new_acc_name) out = get_subscription_by_id(sub_id, **self.new_vo) assert_equal(out['account'], new_acc_name) rules = loads(out['replication_rules'])[0] assert_equal(rules['rse_expression'], self.rse3_name) assert_equal(rules['source_replica_expression'], self.rse4_name) fil = loads(out['filter']) assert_equal(fil['account'], [new_acc_name]) assert_equal(fil['scope'], [new_scope_name])
def POST(self, account, rse): """ Create or update an account limit. HTTP Success: 201 Created HTTP Error: 400 Bad Request 401 Unauthorized 404 Not Found 500 Internal Error :param X-Rucio-Auth-Account: Account identifier. :param X-Rucio-Auth-Token: As an 32 character hex string. :param account: Account name. :param rse: RSE name. """ json_data = data() try: parameter = loads(json_data) except ValueError: raise generate_http_error( 400, 'ValueError', 'cannot decode json parameter dictionary') try: bytes = parameter['bytes'] except KeyError as exception: if exception.args[0] == 'type': raise generate_http_error(400, 'KeyError', '%s not defined' % str(exception)) except TypeError: raise generate_http_error(400, 'TypeError', 'body must be a json dictionary') try: set_local_account_limit(account=account, rse=rse, bytes=bytes, issuer=ctx.env.get('issuer'), vo=ctx.env.get('vo')) except AccessDenied as exception: raise generate_http_error(401, 'AccessDenied', exception.args[0]) except RSENotFound as exception: raise generate_http_error(404, 'RSENotFound', exception.args[0]) except AccountNotFound as exception: raise generate_http_error(404, 'AccountNotFound', exception.args[0]) except Exception as exception: print(format_exc()) raise InternalError(exception) raise Created()
def post(self, account, rse): """ Create or update an account limit. .. :quickref: AccountLimit; Create/update account limits. :param account: Account name. :param rse: RSE name. :status 201: Successfully created or updated. :status 401: Invalid auth token. :status 404: RSE not found. :status 404: Account not found """ json_data = request.data try: parameter = loads(json_data) except ValueError: return generate_http_error_flask( 400, 'ValueError', 'cannot decode json parameter dictionary') try: bytes = parameter['bytes'] except KeyError as exception: if exception.args[0] == 'type': return generate_http_error_flask( 400, 'KeyError', '%s not defined' % str(exception)) except TypeError: return generate_http_error_flask(400, 'TypeError', 'body must be a json dictionary') try: set_local_account_limit(account=account, rse=rse, bytes=bytes, issuer=request.environ.get('issuer'), vo=request.environ.get('vo')) except AccessDenied as exception: return generate_http_error_flask(401, 'AccessDenied', exception.args[0]) except RSENotFound as exception: return generate_http_error_flask(404, 'RSENotFound', exception.args[0]) except AccountNotFound as exception: return generate_http_error_flask(404, 'AccountNotFound', exception.args[0]) except Exception as exception: print(format_exc()) return exception, 500 return "Created", 201
def post(self, account, rse): """ Create or update an account limit. .. :quickref: LocalAccountLimit; Create/update local account limits. :param account: Account name. :param rse: RSE name. :status 201: Successfully created or updated. :status 401: Invalid auth token. :status 404: RSE not found. :status 404: Account not found """ parameters = json_parameters() bytes_param = param_get(parameters, 'bytes') try: set_local_account_limit(account=account, rse=rse, bytes_=bytes_param, issuer=request.environ.get('issuer'), vo=request.environ.get('vo')) except AccessDenied as error: return generate_http_error_flask(401, error) except (RSENotFound, AccountNotFound) as error: return generate_http_error_flask(404, error) return 'Created', 201
def test_api_account_limit(self): """ ACCOUNT_LIMIT (API): Test external representation of account limits """ # Add mock account limits rse_expr = '{}|{}'.format(self.rse_name, self.rse2_name) api_acc_lim.set_local_account_limit(self.account_name, self.rse_name, 10000, issuer='root', **self.vo) api_acc_lim.set_global_account_limit(self.account_name, rse_expr, 20000, issuer='root', **self.vo) out = api_acc_lim.get_local_account_limits(self.account_name, **self.vo) assert_in(self.rse_name, out) assert_not_in(self.rse_id, out) out = api_acc_lim.get_local_account_limit(self.account_name, self.rse_name, **self.vo) assert_in(self.rse_name, out) assert_not_in(self.rse_id, out) out = api_acc_lim.get_global_account_limits(self.account_name, **self.vo) assert_in(rse_expr, out) if self.multi_vo: assert_not_in('vo={}&({})'.format(self.vo['vo'], rse_expr), out) out = api_acc_lim.get_global_account_limit(self.account_name, rse_expr, **self.vo) assert_in(rse_expr, out) if self.multi_vo: assert_not_in('vo={}&({})'.format(self.vo['vo'], rse_expr), out) out = api_acc_lim.get_local_account_usage(self.account_name, self.rse_name, issuer='root', **self.vo) out = list(out) assert_not_equal(0, len(out)) assert_in(self.rse_id, [usage['rse_id'] for usage in out if 'rse_id' in usage]) for usage in out: if 'rse_id' in usage: assert_in('rse', usage) if usage['rse_id'] == self.rse_id: assert_equal(self.rse_name, usage["rse"]) out = api_acc_lim.get_global_account_usage(self.account_name, rse_expr, issuer='root', **self.vo) out = list(out) assert_not_equal(0, len(out)) assert_in(rse_expr, [usage['rse_expression'] for usage in out if 'rse_expression' in usage])
def test_api_account_limit(self): """ ACCOUNT_LIMIT (API): Test external representation of account limits """ # Add mock account limits rse_expr = '{}|{}'.format(self.rse_name, self.rse2_name) api_acc_lim.set_local_account_limit(self.account_name, self.rse_name, 10000, issuer='root', **self.vo) api_acc_lim.set_global_account_limit(self.account_name, rse_expr, 20000, issuer='root', **self.vo) out = api_acc_lim.get_local_account_limits(self.account_name, **self.vo) assert self.rse_name in out assert self.rse_id not in out out = api_acc_lim.get_local_account_limit(self.account_name, self.rse_name, **self.vo) assert self.rse_name in out assert self.rse_id not in out out = api_acc_lim.get_global_account_limits(self.account_name, **self.vo) assert rse_expr in out if self.multi_vo: assert 'vo={}&({})'.format(self.vo['vo'], rse_expr) not in out out = api_acc_lim.get_global_account_limit(self.account_name, rse_expr, **self.vo) assert rse_expr in out if self.multi_vo: assert 'vo={}&({})'.format(self.vo['vo'], rse_expr) not in out out = api_acc_lim.get_local_account_usage(self.account_name, self.rse_name, issuer='root', **self.vo) out = list(out) assert 0 != len(out) assert self.rse_id in [usage['rse_id'] for usage in out if 'rse_id' in usage] for usage in out: if 'rse_id' in usage: assert 'rse' in usage if usage['rse_id'] == self.rse_id: assert self.rse_name == usage["rse"] out = api_acc_lim.get_global_account_usage(self.account_name, rse_expr, issuer='root', **self.vo) out = list(out) assert 0 != len(out) assert rse_expr in [usage['rse_expression'] for usage in out if 'rse_expression' in usage]
def test_subscriptions_at_different_vos(self): """ MULTI VO (CLIENT): Test that subscriptions from 2nd vo don't interfere """ account_client = AccountClient() usr_uuid = str(generate_uuid()).lower()[:16] shr_acc = 'shr-%s' % usr_uuid account_client.add_account(shr_acc, 'USER', '*****@*****.**') add_account(shr_acc, 'USER', '*****@*****.**', 'root', **self.new_vo) scope_client = ScopeClient() scope_uuid = str(generate_uuid()).lower()[:16] tst_scope = 'tst_%s' % scope_uuid new_scope = 'new_%s' % scope_uuid scope_client.add_scope('root', tst_scope) add_scope(new_scope, 'root', 'root', **self.new_vo) did_client = DIDClient() did_uuid = str(generate_uuid()).lower()[:16] tst_did = 'tstset_%s' % did_uuid new_did = 'newset_%s' % did_uuid rse_client = RSEClient() rse_str = ''.join(choice(ascii_uppercase) for x in range(10)) tst_rse1 = 'TST1_%s' % rse_str tst_rse2 = 'TST2_%s' % rse_str new_rse1 = 'NEW1_%s' % rse_str new_rse2 = 'NEW2_%s' % rse_str rse_client.add_rse(tst_rse1) rse_client.add_rse(tst_rse2) add_rse(new_rse1, 'root', **self.new_vo) add_rse(new_rse2, 'root', **self.new_vo) acc_lim_client = AccountLimitClient() acc_lim_client.set_local_account_limit(shr_acc, tst_rse1, 10) acc_lim_client.set_local_account_limit(shr_acc, tst_rse2, 10) set_local_account_limit(shr_acc, new_rse1, 10, 'root', **self.new_vo) set_local_account_limit(shr_acc, new_rse2, 10, 'root', **self.new_vo) did_client.add_did(tst_scope, tst_did, 'DATASET', rse=tst_rse1) add_did(new_scope, new_did, 'DATASET', 'root', rse=new_rse1, **self.new_vo) sub_client = SubscriptionClient() sub_str = generate_uuid() tst_sub = 'tstsub_' + sub_str new_sub = 'newsub_' + sub_str shr_sub = 'shrsub_' + sub_str tst_sub_id = sub_client.add_subscription(tst_sub, shr_acc, {'scope': [tst_scope]}, [{'copies': 1, 'rse_expression': tst_rse2, 'weight': 0, 'activity': 'User Subscriptions'}], '', None, 0, 0) shr_tst_sub_id = sub_client.add_subscription(shr_sub, shr_acc, {'scope': [tst_scope]}, [{'copies': 1, 'rse_expression': tst_rse2, 'weight': 0, 'activity': 'User Subscriptions'}], '', None, 0, 0) new_sub_id = add_subscription(new_sub, shr_acc, {'scope': [new_scope]}, [{'copies': 1, 'rse_expression': new_rse2, 'weight': 0, 'activity': 'User Subscriptions'}], '', False, 0, 0, 3, 'root', **self.new_vo) shr_new_sub_id = add_subscription(shr_sub, shr_acc, {'scope': [new_scope]}, [{'copies': 1, 'rse_expression': new_rse2, 'weight': 0, 'activity': 'User Subscriptions'}], '', False, 0, 0, 3, 'root', **self.new_vo) tst_subs = [s['id'] for s in sub_client.list_subscriptions()] assert_in(tst_sub_id, tst_subs) assert_in(shr_tst_sub_id, tst_subs) assert_not_in(new_sub_id, tst_subs) assert_not_in(shr_new_sub_id, tst_subs) new_subs = [s['id'] for s in list_subscriptions(**self.new_vo)] assert_in(new_sub_id, new_subs) assert_in(shr_new_sub_id, new_subs) assert_not_in(tst_sub_id, new_subs) assert_not_in(shr_tst_sub_id, new_subs) shr_tst_subs = [s['id'] for s in sub_client.list_subscriptions(name=shr_sub)] assert_in(shr_tst_sub_id, shr_tst_subs) assert_not_in(shr_new_sub_id, shr_tst_subs) shr_new_subs = [s['id'] for s in list_subscriptions(name=shr_sub, **self.new_vo)] assert_in(shr_new_sub_id, shr_new_subs) assert_not_in(shr_tst_sub_id, shr_new_subs) acc_tst_subs = [s['id'] for s in sub_client.list_subscriptions(account=shr_acc)] assert_in(tst_sub_id, acc_tst_subs) assert_in(shr_tst_sub_id, acc_tst_subs) assert_not_in(new_sub_id, acc_tst_subs) assert_not_in(shr_new_sub_id, acc_tst_subs) acc_new_subs = [s['id'] for s in list_subscriptions(account=shr_acc, **self.new_vo)] assert_in(new_sub_id, acc_new_subs) assert_in(shr_new_sub_id, acc_new_subs) assert_not_in(tst_sub_id, acc_new_subs) assert_not_in(shr_tst_sub_id, acc_new_subs)