Skip to content

Commit b15a0b3

Browse files
authored
Merge pull request #114 from legend-exp/log
Redirect errors/tracebacks to the right logging stream
2 parents c0c1c5f + 767bd49 commit b15a0b3

File tree

1 file changed

+35
-0
lines changed
  • workflow/src/legenddataflow

1 file changed

+35
-0
lines changed

workflow/src/legenddataflow/log.py

+35
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,28 @@
11
import logging
2+
import sys
3+
import traceback
24
from logging.config import dictConfig
35
from pathlib import Path
46

57
from dbetto import Props
68

79

10+
class StreamToLogger:
11+
"""File-like stream object that redirects writes to a logger instance."""
12+
13+
def __init__(self, logger, log_level=logging.ERROR):
14+
self.logger = logger
15+
self.log_level = log_level
16+
self.linebuf = ""
17+
18+
def write(self, buf):
19+
for line in buf.rstrip().splitlines():
20+
self.logger.log(self.log_level, line.rstrip())
21+
22+
def flush(self):
23+
pass
24+
25+
826
def build_log(
927
config_dict: dict, log_file: str | None = None, fallback: str = "prod"
1028
) -> logging.Logger:
@@ -37,4 +55,21 @@ def build_log(
3755

3856
log = logging.getLogger(fallback)
3957

58+
# Redirect stderr to the logger (using the error level)
59+
sys.stderr = StreamToLogger(log, logging.ERROR)
60+
61+
# Extract the stream from the logger's file handler.
62+
log_stream = None
63+
for handler in log.handlers:
64+
if hasattr(handler, "stream"):
65+
log_stream = handler.stream
66+
break
67+
if log_stream is None:
68+
log_stream = sys.stdout
69+
70+
def excepthook(exc_type, exc_value, exc_traceback):
71+
traceback.print_exception(exc_type, exc_value, exc_traceback, file=log_stream)
72+
73+
sys.excepthook = excepthook
74+
4075
return log

0 commit comments

Comments
 (0)