Python日志模块异常:Anomaly.log重复写入问题求助
Python日志模块异常:Anomaly.log重复写入问题求助
我来帮你排查这个日志重复刷屏的问题~
问题根源
你看哦,你的logger函数被设置成每1秒执行一次,每次运行这个函数的时候,你都会给logger对象新增一个FileHandler指向anomaly.log。执行第N次,就会有N个handler绑定在这个logger上,每次触发日志输出时,所有的handler都会各自写一遍日志,这就是为什么你的anomaly.log会重复刷屏。
而bandit.log用的是logging.basicConfig配置的root logger,这个函数有个特性:只会在第一次调用时生效,后续重复调用不会新增handler,所以它的日志是正常的,不会重复。
解决办法
核心就是把日志的初始化代码(创建logger、添加handler这些)放到函数外面,只执行一次,不要每次调用logger函数都跑一遍。
修改后的完整代码示例:
import pyautogui import schedule import time import logging # 全局变量初始化 call_count = 0 # -------------------------- # 日志配置只执行一次!!! # -------------------------- # 配置bandit.log的root日志 logging.basicConfig(level=logging.INFO, filename="bandit.log", filemode="w", format="%(asctime)s - %(levelname)s - %(message)s") # 配置anomaly.log的专用logger anomaly_logger = logging.getLogger(__name__) anomaly_logger.propagate = False # 阻止日志向上传递到root logger,避免重复写入bandit.log # 给专用logger添加anomaly.log的handler handler = logging.FileHandler('anomaly.log') formatter = logging.Formatter("%(asctime)s - %(name)s - %(levelname)s - %(message)s") handler.setFormatter(formatter) anomaly_logger.addHandler(handler) def logger(): try: # 只执行一次屏幕识别,避免重复消耗资源 location = pyautogui.locateOnScreen('1.png', confidence=0.9) if location: global call_count call_count += 1 anomaly_logger.info(call_count) # 用专用logger写anomaly.log logging.info(call_count) # 这行是写bandit.log的,不需要的话可以删除 except pyautogui.ImageNotFoundException: pass def bandit_cycle(): try: location = pyautogui.locateOnScreen('1.png', confidence=0.9) logging.info('x1 Data found') time.sleep(1.5) except pyautogui.ImageNotFoundException: # 只捕获特定异常,避免隐藏其他错误 pass # 注意:你原代码里的bandit_main未定义,这里改成bandit_cycle(如果是笔误的话) schedule.every(1).seconds.do(bandit_cycle) schedule.every(1).seconds.do(logger) while True: schedule.run_pending() time.sleep(1)
额外优化建议
- 原代码里
logger函数两次调用了pyautogui.locateOnScreen,现在改成先存到变量再判断,减少重复识别的性能消耗。 bandit_cycle里的except:太宽泛了,改成捕获具体的pyautogui.ImageNotFoundException,不然像语法错误、变量未定义这类bug也会被吞掉,不好排查。- 原代码里
schedule.every(1).seconds.do(bandit_main)中的bandit_main函数没有定义,我改成了bandit_cycle,你可以根据实际情况调整。
备注:内容来源于stack exchange,提问作者D3AD_SHOT
相关产品推荐
相关产品推荐

