Sigo haciendo feliz a pylint

This commit is contained in:
Daniel Cortes
2020-06-07 22:29:38 -04:00
parent 40a5d37bb8
commit a0a5857a8b
2 changed files with 53 additions and 39 deletions

View File

@@ -1,5 +1,16 @@
"""Modulo de funciones utilitarias"""
import json
import logging import logging
from collections import Mapping import functools
from multiprocessing.dummy import Pool
from django.http import JsonResponse
from pygments import highlight
from pygments.lexers import JsonLexer # pylint: disable=no-name-in-module
from pygments.formatters import TerminalTrueColorFormatter # pylint: disable=no-name-in-module
_log = logging.getLogger('utils') _log = logging.getLogger('utils')
_log.addHandler(logging.NullHandler()) _log.addHandler(logging.NullHandler())
@@ -7,20 +18,12 @@ _log.addHandler(logging.NullHandler())
def pretty_print_json(json_input): def pretty_print_json(json_input):
"""Formats and prints json to stdout with colors using pygments""" """Formats and prints json to stdout with colors using pygments"""
import json
from pygments import highlight
from pygments.lexers import JsonLexer
from pygments.formatters import TerminalTrueColorFormatter
formatted_json = json.dumps(json_input, indent=2) formatted_json = json.dumps(json_input, indent=2)
print(highlight(formatted_json, JsonLexer(), TerminalTrueColorFormatter())) print(highlight(formatted_json, JsonLexer(), TerminalTrueColorFormatter()))
def message_response(status, error_message): def message_response(status, error_message):
"""Sends an error response with the status code of the error and an explanation""" """Sends an error response with the status code of the error and an explanation"""
from django.http import JsonResponse
json_message = { json_message = {
'status_code': status, 'status_code': status,
'message': error_message 'message': error_message
@@ -29,48 +32,56 @@ def message_response(status, error_message):
return JsonResponse(json_message, status=status) return JsonResponse(json_message, status=status)
# noinspection PyPep8Naming def require_json(function):
def require_JSON(function):
"""Decorator to make a view only accept a json body""" """Decorator to make a view only accept a json body"""
import functools
import json
@functools.wraps(function) @functools.wraps(function)
def decorator(*args, **kwargs): def decorator(*args, **kwargs):
try: try:
received_json = json.loads(args[0].body) received_json = json.loads(args[0].body)
return function(*args, **kwargs, received_json=received_json) return function(*args, **kwargs, received_json=received_json)
except json.JSONDecodeError as error: except json.JSONDecodeError:
_log.warning(f'Function {function.__name__} got a non json request body') _log.warning('Function %s got a non json request body', function.__name__)
return message_response(400, 'Se envío json no valido') return message_response(400, 'Se envío json no valido')
return decorator return decorator
def expected_keys(keys, dictionary): def expected_keys(keys, dictionary):
"""Verifica que un diccionario contiene todas las keys de una lista"""
for key in keys: for key in keys:
if key not in dictionary: if key not in dictionary:
return f'No se encuentra {key}' return f'No se encuentra {key}'
return None return None
def replace_key(json, old, new): def replace_key(dictionary, old, new):
json[new] = json[old] """Remplaza una key en un diccionario
del json[old]
En esencia crea una nueva key con los contenidos de la antigua y elimina la antigua
Esto lo hace inplace por lo que el diccionario es modificado
TODO que cree un nuevo diccionario, es mas bonito el codigo asi
"""
dictionary[new] = dictionary[old]
del dictionary[old]
def sanitize_keys(json): def sanitize_keys(dictionary):
for key in list(json.keys()): """Remplaza las keys de un diccionario que contienen '-' ya que el diccionario pretende
if '-' in key and key in json: ser json y acceder a json con esos caracteres en javascript es incomodo
El diccionario es modificado inplace pero de todas formas se retorna
"""
for key in list(dictionary.keys()):
if '-' in key and key in dictionary:
new_key = key.replace('-', '_') new_key = key.replace('-', '_')
replace_key(json, key, new_key) replace_key(dictionary, key, new_key)
return json return dictionary
def parallel_map(items, function): def parallel_map(items, function):
from multiprocessing.dummy import Pool """Ejecuta una función sobre cada elemento de una lista de items en paralelo utilizando
una Pool del modulo multiprocessing.dummy """
with Pool() as pool: with Pool() as pool:
return pool.map(function, items) return pool.map(function, items)

View File

@@ -1,6 +1,7 @@
"""Modulo que contiene la clase/decorador Cache, contiene su logger y una conexión a redis"""
import json import json
import logging import logging
from blake3 import blake3 from blake3 import blake3 # pylint: disable=no-name-in-module
from redis import Redis from redis import Redis
from django.conf import settings from django.conf import settings
@@ -20,10 +21,10 @@ class Cache:
It is assumed that the function will returns a dictionary that can be formatted to json. It is assumed that the function will returns a dictionary that can be formatted to json.
""" """
"""If caching is enabled""" # If caching is enabled
enabled = settings.CUSTOM_CACHE['enabled'] enabled = settings.CUSTOM_CACHE['enabled']
"""Time to expire, by default a week""" # Time to expire, by default a week
expire = 60 * 60 * 24 * 7 expire = 60 * 60 * 24 * 7
def __init__(self, function): def __init__(self, function):
@@ -34,21 +35,23 @@ class Cache:
_log.info('Cache is disabled, executing function directly') _log.info('Cache is disabled, executing function directly')
return self.function(*args, **kwargs) return self.function(*args, **kwargs)
_log.info(f'Caching function {self.function.__name__} with argument list {args} and dictionary {kwargs}') _log.info('Caching function %s with argument list %s and dictionary %s',
self.function.__name__, args, kwargs)
key = f'{self.function.__name__}:{self.create_hash_key(args, kwargs)}' key = f'{self.function.__name__}:{self.create_hash_key(args, kwargs)}'
_log.debug(f'Resolved key for function is "{key}"') _log.debug('Resolved key for function is "%s"', key)
if _redis.exists(key): if _redis.exists(key):
_log.info(f'Key was in cache') _log.info('Key was in cache')
result = json.loads(_redis.get(key)) result = json.loads(_redis.get(key))
return result return result
else:
_log.info('Key was not in cache') _log.info('Key was not in cache')
result = self.function(*args, **kwargs) result = self.function(*args, **kwargs)
_redis.set(key, json.dumps(result), ex=self.expire) _redis.set(key, json.dumps(result), ex=self.expire)
return result return result
@staticmethod @staticmethod
def create_hash_key(args, kwargs): def create_hash_key(args, kwargs):
"""Crea la key dados unos argumentos arbitrarios"""
return blake3((str(args) + str(kwargs)).encode('utf-8')).hexdigest() return blake3((str(args) + str(kwargs)).encode('utf-8')).hexdigest()