Coverage for /Users/davegaeddert/Development/dropseed/plain/plain/plain/logs/loggers.py: 35%
46 statements
« prev ^ index » next coverage.py v7.6.1, created at 2024-10-16 22:03 -0500
« prev ^ index » next coverage.py v7.6.1, created at 2024-10-16 22:03 -0500
1import logging
3app_logger = logging.getLogger("app")
6class KVLogger:
7 def __init__(self, logger):
8 self.logger = logger
9 self.context = {} # A dict that will be output in every log message
11 def log(self, level, message, **kwargs):
12 msg_kwargs = {
13 **kwargs,
14 **self.context, # Put these last so they're at the end of the line
15 }
16 self.logger.log(level, f"{message} {self._format_kwargs(msg_kwargs)}")
18 def _format_kwargs(self, kwargs):
19 outputs = []
21 for k, v in kwargs.items():
22 self._validate_key(k)
23 formatted_value = self._format_value(v)
24 outputs.append(f"{k}={formatted_value}")
26 return " ".join(outputs)
28 def _validate_key(self, key):
29 if " " in key:
30 raise ValueError("Keys cannot have spaces")
32 if "=" in key:
33 raise ValueError("Keys cannot have equals signs")
35 if '"' in key or "'" in key:
36 raise ValueError("Keys cannot have quotes")
38 def _format_value(self, value):
39 if isinstance(value, str):
40 s = value
41 else:
42 s = str(value)
44 if '"' in s:
45 # Escape quotes and surround it
46 s = s.replace('"', '\\"')
47 s = f'"{s}"'
48 elif s == "":
49 # Quote empty strings instead of printing nothing
50 s = '""'
51 elif any(char in s for char in [" ", "/", "'", ":", "=", "."]):
52 # Surround these with quotes for parsers
53 s = f'"{s}"'
55 return s
57 def info(self, message, **kwargs):
58 self.log(logging.INFO, message, **kwargs)
60 def debug(self, message, **kwargs):
61 self.log(logging.DEBUG, message, **kwargs)
63 def warning(self, message, **kwargs):
64 self.log(logging.WARNING, message, **kwargs)
66 def error(self, message, **kwargs):
67 self.log(logging.ERROR, message, **kwargs)
69 def critical(self, message, **kwargs):
70 self.log(logging.CRITICAL, message, **kwargs)
73# Make this accessible from the app_logger
74app_logger.kv = KVLogger(app_logger)