Worker-side logging/printing integration (internal).
The parent process owns the main logging configuration. The worker routes its own
logging records and print() output into the parent's log queue, so users see a
single unified stream.
Functions
get_logger()
Get or create the brmspy logger instance.
Returns a configured logger with a custom formatter that outputs
messages in the format: [brmspy][method_name] msg here
Returns:
| Type |
Description |
Logger
|
Configured brmspy logger instance
|
Examples:
>>> from brmspy.helpers.log import get_logger
>>> logger = get_logger()
>>> logger.info("Starting process") # Prints: [brmspy][<module>] Starting process
Source code in brmspy/helpers/log.py
| def get_logger() -> logging.Logger:
"""
Get or create the brmspy logger instance.
Returns a configured logger with a custom formatter that outputs
messages in the format: `[brmspy][method_name] msg here`
Returns
-------
logging.Logger
Configured brmspy logger instance
Examples
--------
>>> from brmspy.helpers.log import get_logger
>>> logger = get_logger()
>>> logger.info("Starting process") # Prints: [brmspy][<module>] Starting process
"""
global _logger
if _logger is None:
_logger = logging.getLogger("brmspy")
_logger.setLevel(logging.INFO)
if not _logger.handlers:
# Handler for "normal" logs
normal_handler = logging.StreamHandler()
normal_handler.setFormatter(BrmspyFormatter())
normal_handler.addFilter(NonPrintFilter())
_logger.addHandler(normal_handler)
# print logs: preserve control chars and explicit \n/\r
print_handler = logging.StreamHandler()
print_handler.setFormatter(logging.Formatter("%(message)s"))
print_handler.addFilter(PrintOnlyFilter())
print_handler.terminator = ""
_logger.addHandler(print_handler)
if _running_under_pytest():
_logger.propagate = True
else:
_logger.propagate = False
return _logger
|
setup_worker_logging(log_queue, level=None)
Configure worker logging to forward into the parent's log queue.
Parameters:
| Name |
Type |
Description |
Default |
log_queue
|
Queue
|
Queue owned by the parent; the worker will emit logging records into it.
|
required
|
level
|
int | None
|
Root log level for the worker process. Defaults to logging.INFO.
|
None
|
Notes
When BRMSPY_WORKER=1, the worker replaces builtins.print
to preserve raw control characters and line endings produced by R/cmdstan.
Source code in brmspy/_session/worker/logging.py
| def setup_worker_logging(log_queue: Queue, level: int | None = None) -> None:
"""
Configure worker logging to forward into the parent's log queue.
Parameters
----------
log_queue : multiprocessing.queues.Queue
Queue owned by the parent; the worker will emit `logging` records into it.
level : int | None, optional
Root log level for the worker process. Defaults to `logging.INFO`.
Notes
-----
When `BRMSPY_WORKER=1`, the worker replaces [`builtins.print`](https://docs.python.org/3/library/functions.html#print)
to preserve raw control characters and line endings produced by R/cmdstan.
"""
root = logging.getLogger()
root.handlers.clear()
root.setLevel(level or logging.INFO)
root.addHandler(QueueHandler(log_queue))
logger = get_logger()
def _print(*values: object, **kwargs):
sep = kwargs.get("sep", " ")
end = kwargs.get("end", "\n")
# Preserve raw control chars and end exactly as R/cmdstan intended
msg = sep.join(str(v) for v in values) + end
if msg == "":
return
logger.info(
msg,
extra={
"method_name": "_print",
"no_prefix": True,
"from_print": True, # important for filters
},
)
if os.environ.get("BRMSPY_WORKER") == "1":
builtins.print = _print
|