欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

python3 配置logging日志類的操作

 更新時間:2020年04月08日 09:21:23   作者:耳蟲  
這篇文章主要介紹了python3 配置logging日志類的操作方式,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧

配置類config_file:

from configparser import ConfigParser

class config_file:

  def __init__(self,conf_filePath,encoding="utf-8"):
    #打開配置文件,實例化ConfigParser類,并以默認(rèn)utf-8的編碼格式讀取文件
    self.cf = ConfigParser()
    self.cf.read(conf_filePath,encoding)

  def get_Int_Value(self,section,option):
    #獲取整數(shù)
    return self.cf.getint(section,option)

  def get_boolValue(self,section,option):
    #獲取布爾值
    return self.cf.getboolean(section,option)

  def get_strValue(self,section,option):
    # 獲取字符串類型的值
    return self.cf.get(section,option)

  def get_floatValue(self,section,option):
    # 獲取浮點數(shù)值
    return self.cf.getfloat(section,option)

  def get_sections(self):
    # 獲取所有的section
    return self.cf.sections()

  def get_options(self,section):
    # 獲取所有的option
    return self.cf.options(section)

日志類:

from configparser import ConfigParser
import logging
from config_file import config_file
class Log_Test(config_file):#繼承config_file

  def logging(self):
    logger = logging.getLogger(self.get_strValue('log','logger_name')) #從配置文件讀取logger名
    logger.setLevel(self.get_strValue('log', 'logger_level')) # 設(shè)置logger收集器的收集log級別
    format_logger = logging.Formatter(self.get_strValue('log','logger_format'))
    if(self.get_boolValue('log','logger_out')):
      handle = logging.StreamHandler() # 指定輸出到console控制臺
      handle.setLevel(self.get_strValue('log', 'logger_level')) # 讀取日志等級并設(shè)定logging的級別
      handle.setFormatter(format_logger) # 指定日志格式
    else:
      handle = logging.FileHandler(self.get_strValue('log','logger_filepath'), encoding='utf-8')
      handle.setLevel(self.get_strValue('log', 'logger_level')) # 讀取日志等級并設(shè)定logging的級別
      handle.setFormatter(format_logger) # 指定日志格式
    logger.addHandler(handle)
    return logger

日志配置文件logging.cfg:

[log]
#日志收集器
logger_name=TEST
#日志級別 級別需要大寫 DEBUG-->INFO-->WARNING-->ERROR-->CRITICAL/FATAL
logger_level=DEBUG
#日志輸出格式  注意轉(zhuǎn)義
logger_format=%%(asctime)s-%%(filename)s-%%(levelname)s-日志信息:%%(message)s
#日志是否輸出到控制臺  True  or  False
logger_out=False
#日志輸出指定文件地址
logger_filepath=logging_Test.log

將讀取配置文件類進(jìn)行封裝,日志類繼承配置類。

補充知識:Python2/Python3自定義日志類教程

一、說明

1.1 背景說明

Python的logging功能是比較豐富的支持不同層次的日志輸出,但或是我們想在日志前輸出時間、或是我們想要將日志輸入到文件,我們還是想要自定義日志類。

之前自己也嘗試寫過但感覺文檔太亂看不懂怎么寫,今天有人拿個半成品來問為什么代碼報錯,在其基礎(chǔ)上改造了一下。

1.2 logging級別說明

logging日志級別及對應(yīng)值如下,默認(rèn)情況下直接運行只有INFO及以上級別才會輸出(本質(zhì)上是大于等于20才會輸出),調(diào)試模式運行DEBUG日志才會輸出。

可以通過自定義輸出日志級別,指定直接運行輸出什么級別的日志;不過調(diào)試模式打印的日志應(yīng)該是不可以修改的。

Level

Numeric value

CRITICAL

50

ERROR

40

WARNING

30

INFO

20

DEBUG

10

NOTSET

0

二、實現(xiàn)代碼

2.1 Python2實現(xiàn)代碼

# -*- coding: utf-8 -*-
import os
import datetime
import logging

class LogConfig:
  def __init__(self,log_type="console"):
    # 指定日志輸出到控制臺時的初始化
    if log_type == "console":
      logging.basicConfig(level=logging.INFO,
                format='%(asctime)s %(levelname)s %(message)s',
                datefmt='%Y-%m-%d %H:%M:%S',
                )
    # 指定日志輸出到文件的初始化
    elif log_type == "file":
      # 創(chuàng)建存放日志的目錄
      if not os.path.exists('./log'):
        os.mkdir('./log')

      # 操作系統(tǒng)本身不允許文件名包含:等特殊字符,所以這里也不要用,不然賦給filename時會報錯
      nowTime = datetime.datetime.now().strftime('%Y-%m-%d')
      file_name = './log/%s.log' % nowTime

      # python2.7也有l(wèi)ogging.basicConfig(),但只直接用logging.basicConfig(),寫中文時會報錯
      # 所以為風(fēng)格統(tǒng)一,我們這里不使用logging.basicConfig(),全通過set設(shè)置
      root_logger = logging.getLogger()
      root_logger.setLevel(logging.INFO)
      handler = logging.FileHandler(filename=file_name, encoding='utf-8', mode='a')
      formatter = logging.Formatter('%(asctime)s %(levelname)s %(message)s')
      handler.setFormatter(formatter)
      root_logger.addHandler(handler)

  def getLogger(self):
    logger = logging.getLogger()
    return logger

if __name__ == "__main__":
  # log_type = "console"
  log_type = "file"
  logger = LogConfig(log_type).getLogger()
  logger.debug('print by debug')
  logger.info('print by info')
  logger.warning('print by warning')

2.2 Python3實現(xiàn)代碼

python3.3 之后logging.basicConfig()中提供了handlers參數(shù),我們可借助handlers參數(shù)來指定編碼。

python3.3之前的python3版本寫法得和python2一樣。另外python3.9之后logging.basicConfig()會直接提供encoding參數(shù),到時可以更方便。

import os
import datetime
import logging

class LogConfig:
  def __init__(self,log_type="console"):
    # 指定日志輸出到控制臺時的初始化
    if log_type == "console":
      logging.basicConfig(level=logging.INFO,
                format='%(asctime)s %(levelname)s %(message)s',
                datefmt='%Y-%m-%d %H:%M:%S',
                )
    # 指定日志輸出到文件的初始化
    elif log_type == "file":
      # 創(chuàng)建存放日志的目錄
      if not os.path.exists('./log'):
        os.mkdir('./log')

      # 操作系統(tǒng)本身不允許文件名包含:等特殊字符,所以這里也不要用,不然賦給filename時會報錯
      nowTime = datetime.datetime.now().strftime('%Y-%m-%d')

      file_name = './log/%s.log' % nowTime
      file_handler = logging.FileHandler(filename=file_name,encoding='utf-8', mode='a')
      # level----指定打印的日志等級;默認(rèn)為WARNING;可為NOTSET、DEBUG、INFO、WARNING、ERROR、CRITICAL
      # format----指定整條日志的格式;這里設(shè)置為“時間-等級-日志內(nèi)容”
      # datefmt----format中時間的格式;
      # filename----日志輸出到的文件;默認(rèn)打印到控制臺
      # filemode----日志文件讀寫形式;默認(rèn)為“a”;配合filename使用,如果不用filename該參數(shù)也可不用
      # 本來輸出到文件使用filename和filemode兩個參數(shù)就可以了,不需要handlers
      # 但是logging將日志輸出到文件時中文會亂碼,而logging.basicConfig又沒有提供指定編碼的參數(shù)(python3.9之后才提供有直接的encoding參數(shù))
      # 要指定編碼只能使用handlers。另外handlers還是python3.3 之后才提供的參數(shù),在此之前的版本請參考python2的寫法
      logging.basicConfig(level=logging.INFO,
                format='%(asctime)s %(levelname)s %(message)s',
                datefmt='%Y-%m-%d %H:%M:%S',
                # filename=file_name,
                # filemode='a',
                handlers=[file_handler],
                )

  def getLogger(self):
    logger = logging.getLogger()
    return logger

if __name__ == "__main__":
  # log_type = "console"
  log_type = "file"
  logger = LogConfig(log_type).getLogger()
  logger.debug('print by debug')
  logger.info('print by info')
  logger.warning('print by warning')

三、日志截圖

四、更科學(xué)的日志定義方式(20200310更新)

通過近段時間的使用發(fā)現(xiàn)原先的方法就自己用用沒問題,但與別人產(chǎn)生調(diào)用及上生產(chǎn)時就會存在幾個問題:

第一個問題是,直接通過logging.basicConfig()進(jìn)行配置,會同時影響被調(diào)用庫的日志設(shè)置。

第二個問題是,原現(xiàn)的文件日志形式只能輸出到一個給定的文件,不能實現(xiàn)不同的日志類型輸出到不同的日志文件。

第三個問題是,原現(xiàn)的文件日志形式使用"w"模式則上次日志會被清除,使用"a"模式則日志又會無限增長需要注意清理。

前兩個問題通過getLogger時給定一個名稱而不是直接獲取根logger進(jìn)行處理;第三個問題通過使用TimedRotatingFileHandler等替換FileHandler進(jìn)行處理。

更新代碼如下:

import os
import datetime
import logging
import logging.handlers

class LogConfig:
  def __init__(self):
    pass

  def get_console_logger(self):
    def _gen_file_logger_handler():
      _handler = logging.StreamHandler()
      formatter = logging.Formatter(
        "[%(asctime)s %(msecs)03d][%(process)d][tid=%(thread)d][%(name)s][%(levelname)s] %(message)s [%(filename)s"
        " %(funcName)s %(lineno)s] ", datefmt="%Y-%m-%d %H:%M:%S")
      _handler.setLevel(logging.INFO)
      _handler.setFormatter(formatter)
      return _handler
    def _gen_console_logger():
      # 解決第一個問題--logging.basicConfig()會影響被調(diào)用庫的日志--getLogger時給定一個名稱而不是直接獲取根logger
      _console_logger = logging.getLogger("console_logger")
      _console_logger.addHandler(handler)
      return _console_logger

    handler = _gen_file_logger_handler()
    console_logger = _gen_console_logger()
    return console_logger

  def get_file_logger(self,log_file_name):
    def _make_sure_log_dir_exist():
      if not os.path.isdir(log_file_dir):
        os.mkdir(log_file_dir)
    def _gen_file_logger_handler():
      # 操作系統(tǒng)本身不允許文件名包含:等特殊字符,所以這里也不要用,不然賦給filename時會報錯
      # nowTime = datetime.datetime.now().strftime('%Y-%m-%d')
      file_path = f'{log_file_dir}/{log_file_name}'
      formatter = logging.Formatter(
        "[%(asctime)s %(msecs)03d][%(process)d][tid=%(thread)d][%(name)s][%(levelname)s] %(message)s [%(filename)s"
        " %(funcName)s %(lineno)s] ", datefmt="%Y-%m-%d %H:%M:%S")
      # 解決第三個問題--日志會不斷增大需要手動去清理--使用TimedRotatingFileHandler等替換FileHandler
      # filename----日志文件
      # when----更換日志文件的時間單位
      # interval----更換日志文件的時間單位個數(shù);這里是7天換一個文件
      # backupCount----保存的舊日志文件個數(shù);這里即只保留上一個日志文件
      # encoding----日志文件編碼
      _handler = logging.handlers.TimedRotatingFileHandler(filename=file_path,when='D',interval=7,backupCount=1,encoding='utf-8')
      # 實際發(fā)現(xiàn)有些時候這里setLevel并不起作用
      # _handler.setLevel(logging.INFO)
      _handler.setFormatter(formatter)
      return _handler
    def _gen_file_logger():
      # 解決第二個問題--不能定義多個日志文件--getLogger時給定一個名稱而不是直接獲取根logger
      _file_logger = logging.getLogger(log_file_name)
      _file_logger.addHandler(handler)
      return _file_logger

    log_file_dir = "log"
    _make_sure_log_dir_exist()
    handler = _gen_file_logger_handler()
    file_logger = _gen_file_logger()
    # 實際發(fā)現(xiàn)有些時候handler的setLevel并不起作用,要在這里setLevel
    file_logger.setLevel(logging.INFO)
    return file_logger

if __name__ == "__main__":
  # log_type = "console"
  # logger = LogConfig().get_console_logger()
  log_type = "file"
  # log_file_name不同,返回的是不同的logger,這樣就可以方便地定義多個logger
  log_file_name = "random_file_name.log"
  logger = LogConfig().get_file_logger(log_file_name=log_file_name)
  logger.debug('print by debug')
  logger.info('print by info')
  logger.warning('print by warning')

以上這篇python3 配置logging日志類的操作就是小編分享給大家的全部內(nèi)容了,希望能給大家一個參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • 在Docker上部署Python的Flask框架的教程

    在Docker上部署Python的Flask框架的教程

    這篇文章主要介紹了在Docker上部署Python的Flask框架的教程,包括Docker容器內(nèi)外的網(wǎng)絡(luò)通信等,需要的朋友可以參考下
    2015-04-04
  • Flask框架debug與配置項的開啟與設(shè)置詳解

    Flask框架debug與配置項的開啟與設(shè)置詳解

    這篇文章主要介紹了Flask框架debug與配置項的開啟與設(shè)置,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2022-09-09
  • Python如何將list中的string轉(zhuǎn)換為int

    Python如何將list中的string轉(zhuǎn)換為int

    這篇文章主要介紹了Python如何將list中的string轉(zhuǎn)換為int,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-07-07
  • 使用Tensorflow?hub完成目標(biāo)檢測過程詳解

    使用Tensorflow?hub完成目標(biāo)檢測過程詳解

    這篇文章主要為大家介紹了使用Tensorflow?hub完成目標(biāo)檢測過程詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-04-04
  • Python?lambda函數(shù)使用方法深度總結(jié)

    Python?lambda函數(shù)使用方法深度總結(jié)

    在本文中,小編將帶大家學(xué)習(xí)一下Python中的lambda函數(shù),并探討使用它的優(yōu)點和局限性。文中的示例代碼講解詳細(xì),感興趣的可以了解一下
    2022-05-05
  • Python 可視化matplotlib模塊基礎(chǔ)知識

    Python 可視化matplotlib模塊基礎(chǔ)知識

    這篇文章主要給大家分享的是Python 可視化matplotlib模塊基礎(chǔ)知識,文章對matplotlib.pyplot 模塊繪制相關(guān)如折線、柱狀、散點、圓餅圖表進(jìn)行簡單地學(xué)習(xí),具有一定的參考價值,需要的朋友可以參考一下
    2021-12-12
  • Python中的for循環(huán)詳情

    Python中的for循環(huán)詳情

    這篇文章主要介紹了Python中的for循環(huán),for語句實際上解決的是循環(huán)問題。在很多的高級語言中都有for循環(huán)(for loop)。下面就來簡單給大家介紹Python中的for循環(huán)的相關(guān)資料,需要的朋友可以參考一下
    2021-10-10
  • Python?queue雙端隊列模塊及用法小結(jié)

    Python?queue雙端隊列模塊及用法小結(jié)

    雙端隊列是一種具有隊列和棧性質(zhì)的線性數(shù)據(jù)結(jié)構(gòu),本文主要介紹了Python?queue雙端隊列模塊及用法小結(jié),文中通過示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-02-02
  • Python字符串的修改方法實例

    Python字符串的修改方法實例

    這篇文章主要介紹了Python字符串的修改方法實例,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下
    2019-12-12
  • Scrapy之迭代爬取網(wǎng)頁中失效問題及解決

    Scrapy之迭代爬取網(wǎng)頁中失效問題及解決

    這篇文章主要介紹了Scrapy之迭代爬取網(wǎng)頁中失效問題及解決方案,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-12-12

最新評論