Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/301.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/logging/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/http/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在运行logging.basicConfig之前进行Python日志记录?_Python_Logging - Fatal编程技术网

在运行logging.basicConfig之前进行Python日志记录?

在运行logging.basicConfig之前进行Python日志记录?,python,logging,Python,Logging,如果在运行logging.basicConfig之前调用logging.info(),则logging.basicConfig调用似乎没有任何效果。事实上,没有日志记录发生 这种行为记录在哪里?我真的不明白。是的 你要求记录一些东西。因此,日志记录必须创建默认配置。一旦配置了日志记录。。。好。。。已经配置好了 “配置了记录器对象后, 以下方法创建日志 信息:“ 此外,您还可以阅读有关创建处理程序以防止虚假日志记录的内容。但这与其说是一种有用的技术,不如说是对糟糕实现的攻击 这有个窍门 除了全局级

如果在运行logging.basicConfig之前调用logging.info(),则logging.basicConfig调用似乎没有任何效果。事实上,没有日志记录发生

这种行为记录在哪里?我真的不明白。

是的

你要求记录一些东西。因此,日志记录必须创建默认配置。一旦配置了日志记录。。。好。。。已经配置好了

“配置了记录器对象后, 以下方法创建日志 信息:“

此外,您还可以阅读有关创建处理程序以防止虚假日志记录的内容。但这与其说是一种有用的技术,不如说是对糟糕实现的攻击

这有个窍门

  • 除了全局级别的
    logging.getlogger()
    请求之外,没有任何模块可以执行任何操作

  • 只有
    如果uuuuu name_uuuu==“\uuuuu main\uuuuuu”:
    可以进行日志记录配置

  • 如果您在一个模块中进行全局级别的日志记录,那么您可以强制日志记录以创建其默认配置


    不要在任何模块中全局记录.info。如果您绝对认为必须在模块中具有全局级别的
    logging.info
    ,则必须在执行导入之前配置日志记录。这会导致出现令人不快的脚本。

    您可以删除默认处理程序并重新配置日志记录,如下所示:

    # if someone tried to log something before basicConfig is called, Python creates a default handler that
    # goes to the console and will ignore further basicConfig calls. Remove the handler if there is one.
    root = logging.getLogger()
    if root.handlers:
        for handler in root.handlers:
            root.removeHandler(handler)
    logging.basicConfig(format='%(asctime)s %(message)s',level=logging.DEBUG)
    

    这是上面答案没有提到的谜题的一部分。。。然后一切都会变得有意义:“root”记录器——如果在logging.basicConfig(level=logging.DEBUG)之前调用logging.info(),则使用它——具有默认的日志级别警告

    这就是为什么logging.info()和logging.debug()不做任何事情的原因:因为您已经将它们配置为不做任何事情,通过。。。嗯。。。没有配置它们


    可能相关(这一点对我有点影响):当不调用basicConfig时,我似乎没有收到调试消息,即使我将处理程序设置为调试级别。在做了一点尝试之后,我发现您还必须将自定义记录器的级别设置为DEBUG。如果您的记录器设置为警告,那么将处理程序设置为调试(本身)将不会在logger.info()和logger.DEBUG()上获得任何输出。

    Carlos a.Ibarra的回答原则上是正确的,但是,由于您正在迭代一个列表,而该列表可能会通过调用removeHandler()进行更改,因此该实现可能会中断。这是不安全的。 两个备选方案是:

    while len(logging.root.handlers) > 0:
        logging.root.removeHandler(logging.root.handlers[-1])
    logging.basicConfig(format='%(asctime)s %(message)s',level=logging.DEBUG)
    
    或:


    其中,使用循环的这两种方法中的第一种是最安全的(因为处理程序的任何销毁代码都可以在日志框架内显式调用)。尽管如此,这还是一种黑客行为,因为我们依赖logging.root.handlers作为列表。

    对于@paul kremer给出的答案,更清晰的版本是:

    while len(logging.root.handlers):
        logging.root.removeHandler(logging.root.handlers[-1])
    

    注意:通常可以安全地假设logging.root.handlers始终是一个列表(请参阅:)

    今天遇到了同样的问题,作为上述答案的替代方案,这里是我的解决方案

    导入日志
    导入系统
    logging.debug('foo')#IRL,此调用来自导入的模块
    如果uuuu name uuuuuu='\uuuuuuu main\uuuuuuu':
    logging.basicConfig(level=logging.INFO,force=True)
    logging.info('bar')#如果不使用force=True,则不会将其打印到控制台
    
    下面是关于
    force
    参数的说明

    如果此关键字参数指定为true,则所有现有处理程序 在搬运之前,移除并关闭与根记录器相连的组件 按其他参数指定的方式输出配置

    这就是我所做的

    我想登录到一个配置文件中配置了名称的文件,并获取配置解析的调试日志

    TL;博士这将登录到缓冲区,直到配置记录器的所有内容都可用为止

    #将所有内容记录到内存处理器中,直到真正的记录器准备就绪。
    #MemoryHandler从不自动刷新(flushLevel 100高于临界值),但仅在关闭时刷新。
    #如果配置加载成功,则实际记录器将被配置并设置为MemoryHandler的目标
    #在它通过关闭被刷新之前。
    #这意味着,如果日志到达标准输出,它将不按级别进行过滤
    root_logger=logging.getLogger()
    root_logger.setLevel(logging.NOTSET)
    stdout\u logging\u handler=logging.StreamHandler(sys.stderr)
    tmp_logging_handler=logging.handler.MemoryHandler(1024*1024,100,stdout_logging_handler)
    root_logger.addHandler(tmp_logging_handler)
    config:ApplicationConfig=ApplicationConfig.from_文件名('config.ini'))
    #因为这些记录已经被记录,所以不需要的记录需要被删除
    filtered_buffer=filter(lambda记录:record.levelno>=config.main_config.log_level,tmp_logging_handler.buffer)
    tmp_logging_handler.buffer=过滤的_缓冲区
    root_logger.removeHandler(tmp_logging_handler)
    logging.basicConfig(filename=config.main\u config.log\u filename,level=config.main\u config.log\u level,filemode='wt')
    日志处理程序=根日志处理程序。处理程序[0]
    tmp_logging_handler.setTarget(logging_handler)
    tmp_logging_handler.close()
    stdout\u日志记录\u处理程序.close()
    
    不,我错了-显然这是设计上的,因为basicConfig是从.info等调用的,以确保安装了记录器。对我来说,这似乎仍然是一种奇怪的行为。如果你-像我一样-尝试重用以前的记录器,实例化如下:
    logger=logging.getLogger(\uuuu name\uuuu)
    并尝试循环
    logger.handlers
    ,它将不起作用。“If root.handlers:”有什么好处?迭代空序列没有效果。是否可能root.handlers是其他非序列假值?(它不在我的系统上)用于调试AWS Lambdas的日志记录问题。看起来他们在lambda引导期间安装了一些名为
    LambdaLoggingHandler
    的处理程序。删除已安装的处理程序解决了问题。还可以执行
    list(logging.root.handlers)
    来制作副本这是正确的现代解决方案-但它仅适用于Python>=3.8
    while len(logging.root.handlers):
        logging.root.removeHandler(logging.root.handlers[-1])