Strange logging.Formatter behaviour

Vinay Sajip vinay_sajip at yahoo.co.uk
Tue Nov 22 11:21:10 EST 2011


On Nov 22, 3:19 pm, Tiaburn Stedd <aleksandrs.zdanc... at gmail.com>
wrote:
> I don't believe this behavior is normal. I expect error raised in a
> Formatter.format function, should be passed all the way up, but not
> consumed.
>
> I found a workaround:
>
> class CustomFileHandler(logging.FileHandler, object):
>     def handleError(self, record):
>          super(CustomFileHandler, self).handleError(record)
>          raise
>
> But it looks ugly to add Custom*Handler for any default Handler (like,
> StreamHandler, etc) to make them possible to fall out on any error.
>
> There are raiseException switch in source of logging/__init__.py
>
>   92 #raiseExceptions is used to see if exceptions during handling
> should be
>   93 #propagated
>   94 #
>   95 raiseExceptions = 1
>
> But all it switch is only is traceback printed or not. I think this
> behaviour is against Zen of Python: "Errors should never pass
> silently."

They don't pass silently - raiseExceptions defaults to 1, so
tracebacks are printed by default. In production, it's not a good idea
for a potentially long-running process like a server to be brought
down because someone put a typo in a logging format string, so the
recommendation is to set raiseExceptions to 0/False in such scenarios.

Since you are developing a custom formatter, you can certainly catch
any formatting exceptions in your format method and decide what you
want to do with them.

The default handleError behaviour of printing a traceback is
reasonable, in my view. If you want something else, you can subclass
the relevant handler class; just setting a printTracebacks flag to
false isn't going to get useful behaviour specific to individual
requirements.

There's no real point in throwing a very specific exception from a
formatter, as a handler isn't going to automatically know how to
handle a SpecificFormatException in any meaningful way. Remember that
in the general case, application developers don't always have control
of what handlers are configured for an application (for example, this
could be set by end-user or per-deployment configuration).

Regards,

Vinay Sajip



More information about the Python-list mailing list