我试图用Python的日志记录模块替换临时日志记录系统。我正在使用日志记录系统在单行上输出长时间任务的进度信息,因此您可以在日志中或在控制台中观看日志。我通过在我的日志记录功能上设置了一个标志来抑制该日志消息的换行符并逐个构建行。在Python日志记录模块中取消换行
所有的日志都是从一个线程完成的,所以没有序列化问题。
是否可以使用Python的日志记录模块做到这一点?这是个好主意吗?
我试图用Python的日志记录模块替换临时日志记录系统。我正在使用日志记录系统在单行上输出长时间任务的进度信息,因此您可以在日志中或在控制台中观看日志。我通过在我的日志记录功能上设置了一个标志来抑制该日志消息的换行符并逐个构建行。在Python日志记录模块中取消换行
所有的日志都是从一个线程完成的,所以没有序列化问题。
是否可以使用Python的日志记录模块做到这一点?这是个好主意吗?
让我们从最后一个问题开始:不,我不相信这是个好主意。 国际海事组织,从长远看,它伤害了日志文件的可读性。
我建议坚持使用logging模块并在'tail'命令中使用'-f'选项来观察控制台的输出。您可能最终会使用FileHandler。注意'delay'的默认参数是False,这意味着输出不会被缓冲。
如果你真的需要抑制换行符,我会建议创建自己的Handler。
将新行\n
插入StreamHandler
类中。
如果你真的设置固定这种行为,那么这里的我是如何解决这个由monkey patching的logging.StreamHandler类中的emit(self, record)
方法的例子。
猴子补丁是一种扩展或修改动态语言的运行时代码而不改变原始源代码的方法。这个过程也被称为鸭子冲压。
这里是emit()
自定义实现省略了换行:
def customEmit(self, record):
# Monkey patch Emit function to avoid new lines between records
try:
msg = self.format(record)
if not hasattr(types, "UnicodeType"): #if no unicode support...
self.stream.write(msg)
else:
try:
if getattr(self.stream, 'encoding', None) is not None:
self.stream.write(msg.encode(self.stream.encoding))
else:
self.stream.write(msg)
except UnicodeError:
self.stream.write(msg.encode("UTF-8"))
self.flush()
except (KeyboardInterrupt, SystemExit):
raise
except:
self.handleError(record)
然后你会做一个自定义日志记录类(在这种情况下,从TimedRotatingFileHandler
子类)。
class SniffLogHandler(TimedRotatingFileHandler):
def __init__(self, filename, when, interval, backupCount=0,
encoding=None, delay=0, utc=0):
# Monkey patch 'emit' method
setattr(StreamHandler, StreamHandler.emit.__name__, customEmit)
TimedRotatingFileHandler.__init__(self, filename, when, interval,
backupCount, encoding, delay, utc)
有些人可能会认为,这种类型的解决方案是不Python的,或什么的。可能是这样,所以要小心。
另外,请注意,这将全局修补SteamHandler.emit(...)
,所以如果您使用多个日志记录类,那么此修补程序也会影响其他日志记录类!
查阅这些进一步阅读:
希望有所帮助。
如果您想这样做,您可以更改日志处理程序终止符。我正在使用Python 3.4。正如Ninjakannon所述,它是在Python 3.2中引入的。
handler = logging.StreamHandler()
handler.terminator = ""
当StreamHandler写入它时,最后写入终止符。
这是[在Python 3.2中引入的](https://docs.python.org/3/library/logging.handlers.html#streamhandler)。 – Ninjakannon
如果您想在同一行中记录多个事物,请考虑不要使用'logging',而是使用一个好的旧文件对象并直接写入它(并将其写入到与其他基于行的日志文件不同的文件中,东西)。 – ThiefMaster
@ThiefMaster我现在正在写一个文件和stdout。这感觉就像我正在重写日志记录,所以我宁愿使用日志记录,如果它结束了更少的努力。 –