예제 #1
0
 def __init__(self, request):
     self.request = request
     self._settings = request.registry.settings
     self._data = self._settings['data']
     self.accounting = Accounting()
     self.authentication = AuthenticationManager()
     self.token = Token()
예제 #2
0
class AccountingRestView:
    """
    Implements the main REST API.
    """
    def __init__(self, request):
        self.request = request
        self._settings = request.registry.settings
        self._data = self._settings['data']
        self.accounting = Accounting()
        self.authentication = AuthenticationManager()
        self.token = Token()

    @view_config(route_name=Route.READ_ACCOUNTING,
                 request_method='POST',
                 renderer='json')
    def get(self):
        """ 
        This method is called from **/engine/api/get_accounting_data**.
        This method is called in order to get accounting information from user.

        Arguments:
            username (str): the username;

        Returns:
            success (bool): True if sucessfully get accounting information and 
            False otherwise;
            error (str): an error message if an error occured and an empty
            string otherwise.
        """
        msg = ''
        try:
            username = self.request.params['username']
            token = self.request.params['token']
            usr = self.token.verify_token(2, token)
            if usr != 'invalid token' and usr == username:
                data = self.accounting.get(username)
                if data is not None:
                    return {
                        'success':
                        'User accounting information read successfully.',
                        'data': json.dumps(data)
                    }
                else:
                    return {'error': 'Accounting information not found.'}
        except KeyError as e:
            msg = 'Missing mandatory parameter: ' + str(e)
            raise e
        except Exception as e:
            msg = 'Unknown error occurred: ' + str(e)
            raise e
        LOG.info(msg)
        return {'error': msg}
예제 #3
0
class Authorisation:
    """
    Authorisation class is responsible for managing resource usage rules.
    """
    def __init__(self):
        self.basedb = BaseDB()
        self.accounting = Accounting()

    def verify(self, username, resource_name, resource_category):
        """
        Returns True if username is allowed to access resource.
        """
        resources = list(
            self.basedb.get(AUTHORISATION_COLLECTION, AUTHORISATION_KEY,
                            username))
        for item in resources:
            for elem in item['resource_rule']:
                LOG.info('elem: %s' % elem)
                if elem['resource_name'] == resource_name and\
                    elem['resource_category'] == resource_category:
                    return True
        return False

    def update_resource_item(self, username, resource_name, resource_category):
        """
        Add 1 to used field.
        """
        resources = self.basedb.get(AUTHORISATION_COLLECTION,
                                    AUTHORISATION_KEY, username)
        for item in resources:
            for elem in item['resource_rule']:
                LOG.info('elem: %s' % elem)
                if elem['resource_name'] == resource_name and\
                        elem['resource_category'] == resource_category:
                    old_item = copy.deepcopy(item)
                    elem['used'] = elem['used'] + 1
                    res = self.basedb.update(AUTHORISATION_COLLECTION,
                                             AUTHORISATION_KEY, username,
                                             AUTHORISATION_ITEM, old_item,
                                             item)
        return res

    def use_resource(self, username, resource_name, resource_category):
        """
        This method is called in order to user a determined resource. Thus, it
        is responsible for triggering the accounting mechanism and updating the
        database to increment the number of times that resource was used. 
        """
        if self.verify(username, resource_name, resource_category):
            # add 1 to used field
            self.update_resource_item(username, resource_name,
                                      resource_category)
            # account it
            msg = "Resource " + resource_name + " used by: " + username + "."
            LOG.info('msg: %s' % msg)
            category = INFO
            self.accounting.register(username, msg, category)
            return {'msg': msg}
        return None

    def validate_rule(self, rule):
        """
        Validates authorisation object.
        """

        SCHEMA = {
            'type': 'object',
            'properties': {
                'resource_name': {
                    'type': 'string',
                    'minLength': 1,
                    'maxLength': 50
                },
                'resource_category': {
                    'type': 'string',
                    'minLength': 1,
                    'maxLength': 50
                },
                'max_used': {
                    'type': 'number'
                },
                'used': {
                    'type': 'number'
                },
            },
            'required': ['resource_category', 'resource_name', 'max_used']
        }
        try:
            validate(rule, SCHEMA)
        except ValidationError as err:
            LOG.error('Invalid rule')
            raise Exception('Invalid rule') from err
        return True

    def create(self, username, resource_category, resource_name, max_used):
        """
        Create an authorisation rule on database. 

        Args:
            username (str): username;
            resource_name (str): name that identifies the resource being used;
            rule (dict): rule object.

        Returns:
            database response
        """
        rule = {
            'resource_category': resource_category,
            'resource_name': resource_name,
            'max_used': int(max_used),
            'used': 0
        }
        if self.validate_rule(rule):
            result = self.basedb.insert(AUTHORISATION_COLLECTION,
                                        AUTHORISATION_KEY, username,
                                        AUTHORISATION_ITEM, rule)
            if result is not None:
                LOG.info('Rule: ' + json.dumps(rule) +
                         'successfully created for user: '******'.')
                return result
        return None

    def read(self, username, resource_name, resource_category):
        """
        Read rule information from user.
        """
        resources = self.basedb.get(AUTHORISATION_COLLECTION,
                                    AUTHORISATION_KEY, username)
        for item in resources:
            for elem in item[AUTHORISATION_ITEM]:
                if elem['resource_name'] == resource_name and\
                        elem['resource_category'] == resource_category:
                    return elem
        return None

    def update(self, username, resource_name, resource_category, max_allowed):
        """
        Update rule information. 
        """
        resources = self.basedb.get(AUTHORISATION_COLLECTION,
                                    AUTHORISATION_KEY, username)
        for item in resources:
            for elem in item[AUTHORISATION_ITEM]:
                if elem['resource_name'] == resource_name and\
                        elem['resource_category'] == resource_category:
                    new_elem = copy.deepcopy(elem)
                    new_elem['max_allowed'] = max_allowed
                    result = self.basedb.update(AUTHORISATION_COLLECTION,
                                                AUTHORISATION_KEY, username,
                                                AUTHORISATION_ITEM, elem,
                                                new_elem)
                    return result
        return None

    def delete(self, username, resource_name, resource_category):
        """
        Delete rule information. 
        """
        resources = self.basedb.get(AUTHORISATION_COLLECTION,
                                    AUTHORISATION_KEY, username)
        for item in resources:
            for elem in item[AUTHORISATION_ITEM]:
                if elem['resource_name'] == resource_name and\
                        elem['resource_category'] == resource_category:
                    result = self.basedb.remove_list_item(
                        AUTHORISATION_COLLECTION, AUTHORISATION_KEY, username,
                        AUTHORISATION_ITEM, elem)
                    return result
        return None
예제 #4
0
 def __init__(self):
     self.basedb = BaseDB()
     self.accounting = Accounting()
예제 #5
0
def step_impl(context):
    with patch.object(BaseDB, 'insert', return_value=True) as mck_insert:
        accounting = Accounting()
        accounting.register(context.username, context.msg, context.category)
        assert mck_insert.called