<commit_before>from flask_restful import Resource, request, abort
from flask_restful_swagger import swagger

import requests

from hpcpm.api import log
from hpcpm.api.helpers.database import database
from hpcpm.api.helpers.utils import abort_when_node_not_found
from hpcpm.api.helpers.requests import delete_power_limit
from hpcpm.api.helpers.constants import COMPUTATION_NODE_PARAM_NAME, COMPUTATION_NODE_NOT_FOUND_RESPONSE, \
    COMPUTATION_NODE_FETCHED_RESPONSE, DEVICE_IDENTIFIER_PARAM, RULE_TYPE_PARAM, RULE_PARAMS_PARAM, \
    RULE_SET_RESPONSE, DEVICE_NOT_FOUND_RESPONSE, \
    NODE_AND_DEVICE_PARAMS, AVAILABLE_RULE_TYPES, DEVICE_NOT_FOUND_AND_COMPUTATION_NODE_FETCHED_RESPONSES


class Rule(Resource):
    @swagger.operation(
        notes='This endpoint is used for setting rule for given device.',
        nickname='/nodes/computation_node/<string:name>/<string:device_id>/rule',
        parameters=[
            COMPUTATION_NODE_PARAM_NAME,
            DEVICE_IDENTIFIER_PARAM,
            RULE_PARAMS_PARAM,
            RULE_TYPE_PARAM
        ],
        responseMessages=[
            COMPUTATION_NODE_NOT_FOUND_RESPONSE,
            RULE_SET_RESPONSE
        ]
    )
    def put(self, name, device_id):
        rule_type = request.args.get('rule_type')
        rule_params = request.json
        if rule_type not in AVAILABLE_RULE_TYPES:
            abort(400)
        computation_node = abort_when_node_not_found(name)

        if not any(d['id'] == device_id for d in computation_node['backend_info']['devices']):
            log.error('There is no such device: %s', device_id)
            abort(404)

        if rule_type == "Withdrawable":
            previous_rule = database.get_rule_for_device(name, device_id)
            if previous_rule:
                if previous_rule["rule_type"] == "Withdrawable":
                    previous_rule = previous_rule["rule_params"].get("previous_rule", None)
                rule_params["previous_rule"] = previous_rule

        database.replace_rule_for_device(name, device_id, {'name': name, 'device_id': device_id, 'rule_type': rule_type,
                                                           'rule_params': rule_params})<commit_msg>Ability to set limit to HIGH, MEDIUM or LOW<commit_after>from flask_restful import Resource, request, abort
from flask_restful_swagger import swagger

import requests

from hpcpm.api import log
from hpcpm.api.helpers.database import database
from hpcpm.api.helpers.utils import abort_when_node_not_found, get_com_node_and_dev_type
from hpcpm.api.helpers.requests import delete_power_limit, get_constraints
from hpcpm.api.helpers.constants import COMPUTATION_NODE_PARAM_NAME, COMPUTATION_NODE_NOT_FOUND_RESPONSE, \
    COMPUTATION_NODE_FETCHED_RESPONSE, DEVICE_IDENTIFIER_PARAM, RULE_TYPE_PARAM, RULE_PARAMS_PARAM, \
    RULE_SET_RESPONSE, DEVICE_NOT_FOUND_RESPONSE, \
    NODE_AND_DEVICE_PARAMS, AVAILABLE_RULE_TYPES, DEVICE_NOT_FOUND_AND_COMPUTATION_NODE_FETCHED_RESPONSES


class Rule(Resource):
    @swagger.operation(
        notes='This endpoint is used for setting rule for given device.',
        nickname='/nodes/computation_node/<string:name>/<string:device_id>/rule',
        parameters=[
            COMPUTATION_NODE_PARAM_NAME,
            DEVICE_IDENTIFIER_PARAM,
            RULE_PARAMS_PARAM,
            RULE_TYPE_PARAM
        ],
        responseMessages=[
            COMPUTATION_NODE_NOT_FOUND_RESPONSE,
            RULE_SET_RESPONSE
        ]
    )
    def put(self, name: str, device_id: str):
        rule_type = request.args.get('rule_type')
        rule_params = request.json
        if rule_type not in AVAILABLE_RULE_TYPES:
            abort(400)
        computation_node = abort_when_node_not_found(name)

        if not any(d['id'] == device_id for d in computation_node['backend_info']['devices']):
            log.error('There is no such device: %s', device_id)
            abort(404)

        limit = rule_params.get("limit")
        if limit in {"HIGH", "MEDIUM", "LOW"}:
            computation_node, dev_type = get_com_node_and_dev_type(name, device_id)
            constraints = get_constraints(
                computation_node['address'],
                computation_node['port'], device_id, dev_type).json()[0]["PowerLimitConstraints"]
            lower = constraints["lower"]
            upper = constraints["upper"]
            if limit == "HIGH":
                rule_params["limit"] = upper
            elif limit == "MEDIUM":
                rule_params["limit"] = (upper + lower) / 2
            elif limit == "LOW":
                rule_params["limit"] = lower

        if rule_type == "Withdrawable":
            previous_rule = database.get_rule_for_device(name, device_id)
            if previous_rule:
                if previous_rule["rule_type"] == "Withdrawable":
                    previous_rule = previous_rule["rule_params"].get("previous_rule", None)
                rule_params["previous_rule"] = previous_rule

        database.replace_rule_for_device(name, device_id, {'name': name, 'device_id': device_id, 'rule_type': rule_type,
                                                           'rule_params': rule_params})
{'fraction_non_alphanumeric': 0.08531171588496429, 'fraction_numerical': 0.0027021810461300907, 'mean_word_length': 2.87584143605086, 'pattern_counts': {'":': 7, '<': 7, '<?xml version=': 0, '>': 7, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2275739', 'n_tokens_mistral': 1595, 'n_tokens_neox': 1573, 'n_words': 294}