Пример #1
0
 def test_global_account_limits(self):
     """ ACCOUNT_LIMIT (CORE): Set, get and delete global account limits """
     resolved_rse_ids = [get_rse_id('MOCK', **self.vo)]
     resolved_rses = ['MOCK']
     limit = 10
     account_limit.set_global_account_limit(self.account, 'MOCK', limit, session=self.db_session)
     results = account_limit.get_global_account_limits(account=self.account, session=self.db_session)
     assert len(results) == 1
     assert 'MOCK' in results
     assert results['MOCK']['resolved_rses'] == resolved_rses
     assert results['MOCK']['resolved_rse_ids'] == resolved_rse_ids
     assert results['MOCK']['limit'] == limit
     account_limit.delete_global_account_limit(self.account, 'MOCK', session=self.db_session)
     results = account_limit.get_global_account_limits(account=self.account, session=self.db_session)
     assert len(results) == 0
Пример #2
0
 def test_global_account_limits(self):
     """ ACCOUNT_LIMIT (CORE): Set, get and delete global account limits """
     resolved_rse_ids = [get_rse_id('MOCK', **self.vo)]
     resolved_rses = ['MOCK']
     limit = 10
     account_limit.set_global_account_limit(self.account,
                                            'MOCK',
                                            limit,
                                            session=self.db_session)
     results = account_limit.get_global_account_limits(
         account=self.account, session=self.db_session)
     assert_equal(len(results), 1)
     assert_in('MOCK', results)
     assert_equal(results['MOCK']['resolved_rses'], resolved_rses)
     assert_equal(results['MOCK']['resolved_rse_ids'], resolved_rse_ids)
     assert_equal(results['MOCK']['limit'], limit)
     account_limit.delete_global_account_limit(self.account,
                                               'MOCK',
                                               session=self.db_session)
     results = account_limit.get_global_account_limits(
         account=self.account, session=self.db_session)
     assert_equal(len(results), 0)
Пример #3
0
def get_global_account_limits(account):
    """
    Lists the limitation names/values for the specified account name.

    REST API: http://<host>:<port>/rucio/account/<account>/limits

    :param account:     The account name.

    :returns: The account limits.
    """

    account = InternalAccount(account)
    return account_limit_core.get_global_account_limits(account=account)
Пример #4
0
def get_global_account_limits(account, vo='def'):
    """
    Lists the limitation names/values for the specified account name.

    REST API: http://<host>:<port>/rucio/account/<account>/limits

    :param account:     The account name.
    :param vo:          The VO to act on.

    :returns: The account limits.
    """
    if account:
        account = InternalAccount(account, vo=vo)
    else:
        account = InternalAccount('*', vo=vo)

    return account_limit_core.get_global_account_limits(account=account)
Пример #5
0
    def __init__(self,
                 account,
                 rses,
                 weight,
                 copies,
                 ignore_account_limit=False,
                 session=None):
        """
        Initialize the RSE Selector.

        :param account:               Account owning the rule.
        :param rses:                  List of rse dictionaries.
        :param weight:                Weighting to use.
        :param copies:                Number of copies to create.
        :param ignore_account_limit:  Flag if the quota should be ignored.
        :param session:               DB Session in use.
        :raises:                      InvalidRuleWeight, InsufficientAccountLimit, InsufficientTargetRSEs
        """
        self.account = account
        self.rses = []  # [{'rse_id':, 'weight':, 'staging_area'}]
        self.copies = copies
        if weight is not None:
            for rse in rses:
                attributes = list_rse_attributes(rse_id=rse['id'],
                                                 session=session)
                availability_write = True if rse.get('availability',
                                                     7) & 2 else False
                if weight not in attributes:
                    continue  # The RSE does not have the required weight set, therefore it is ignored
                try:
                    self.rses.append({
                        'rse_id': rse['id'],
                        'weight': float(attributes[weight]),
                        'mock_rse': attributes.get('mock', False),
                        'availability_write': availability_write,
                        'staging_area': rse['staging_area']
                    })
                except ValueError:
                    raise InvalidRuleWeight(
                        'The RSE \'%s\' has a non-number specified for the weight \'%s\''
                        % (rse['rse'], weight))
        else:
            for rse in rses:
                mock_rse = has_rse_attribute(rse['id'],
                                             'mock',
                                             session=session)
                availability_write = True if rse.get('availability',
                                                     7) & 2 else False
                self.rses.append({
                    'rse_id': rse['id'],
                    'weight': 1,
                    'mock_rse': mock_rse,
                    'availability_write': availability_write,
                    'staging_area': rse['staging_area']
                })

        if len(self.rses) < self.copies:
            raise InsufficientTargetRSEs(
                'Target RSE set not sufficient for number of copies. (%s copies requested, RSE set size %s)'
                % (self.copies, len(self.rses)))

        rses_with_enough_quota = []
        if has_account_attribute(account=account, key='admin',
                                 session=session) or ignore_account_limit:
            for rse in self.rses:
                rse['quota_left'] = float('inf')
                rse['space_left'] = float('inf')
                rses_with_enough_quota.append(rse)
        else:
            global_quota_limit = get_global_account_limits(account=account,
                                                           session=session)
            all_rse_usages = {
                usage['rse_id']: usage['bytes']
                for usage in get_all_rse_usages_per_account(account=account,
                                                            session=session)
            }
            for rse in self.rses:
                if rse['mock_rse']:
                    rse['quota_left'] = float('inf')
                    rse['space_left'] = float('inf')
                    rses_with_enough_quota.append(rse)
                else:
                    # check local quota
                    local_quota_left = None
                    quota_limit = get_local_account_limit(account=account,
                                                          rse_id=rse['rse_id'],
                                                          session=session)
                    if quota_limit is None:
                        local_quota_left = 0
                    else:
                        local_quota_left = quota_limit - get_usage(
                            rse_id=rse['rse_id'],
                            account=account,
                            session=session)['bytes']

                    # check global quota
                    rse['global_quota_left'] = {}
                    all_global_quota_enough = True
                    for rse_expression, limit in global_quota_limit.items():
                        if rse['rse_id'] in limit['resolved_rse_ids']:
                            quota_limit = limit['limit']
                            global_quota_left = None
                            if quota_limit is None:
                                global_quota_left = 0
                            else:
                                rse_expression_usage = 0
                                for rse_id in limit['resolved_rse_ids']:
                                    rse_expression_usage += all_rse_usages.get(
                                        rse_id, 0)
                                global_quota_left = quota_limit - rse_expression_usage
                            if global_quota_left <= 0:
                                all_global_quota_enough = False
                                break
                            else:
                                rse['global_quota_left'][
                                    rse_expression] = global_quota_left
                    if local_quota_left > 0 and all_global_quota_enough:
                        rse['quota_left'] = local_quota_left
                        space_limit = get_rse_limits(
                            name='MaxSpaceAvailable',
                            rse_id=rse['rse_id'],
                            session=session).get('MaxSpaceAvailable')
                        if space_limit is None or space_limit < 0:
                            rse['space_left'] = float('inf')
                        else:
                            rse['space_left'] = space_limit - get_rse_counter(
                                rse_id=rse['rse_id'], session=session)['bytes']
                        rses_with_enough_quota.append(rse)

        self.rses = rses_with_enough_quota
        if len(self.rses) < self.copies:
            raise InsufficientAccountLimit(
                'There is insufficient quota on any of the target RSE\'s to fullfill the operation.'
            )