python - 如何在 Python 中的函数入口、内部和导出处进行日志记录

标签 python logging

我希望能够使用 Python 日志工具在我的代码中进行简单且一致的日志记录。

我可以做到以下几点:

  1. 我希望所有现有/ future 的模块和功能都具有“进入...”和“完成...”日志消息。
  2. 我不想在每个函数定义中添加相同的代码片段来定义日志记录参数(如下所示不想在任何地方添加)。
  3. 我希望 log.info(...) 等构造在我在项目层次结构中定义的任何函数中工作。

什么不起作用/我不知道该怎么做:

  1. 我想避免在我编写的每个现有/新模块中定义相同的 @log 装饰器。
# don't want to add everywhere
FORMAT = '%(asctime)s - %(name)-20s - %(levelname)-5s - %(message)s'
LEVEL = logging.DEBUG
logging.basicConfig(format=FORMAT, level=LEVEL)
log = logging.getLogger(__name__)

**我的 Flask 项目中的示例代码:**
# app/__init__.py
from a import b  # various other imports required for app
import logging
FORMAT = '%(asctime)s - %(name)-20s - %(levelname)-5s - %(message)s'
LEVEL = logging.DEBUG
logging.basicConfig(format=FORMAT, level=LEVEL)
log = logging.getLogger(__name__)
# ... various other app init code
from app import views, models
#app/views.py
from c import d  # various other imports required for the module

def logger(fn):
    from functools import wraps
    import inspect
    @wraps(fn)
    def wrapper(*args, **kwargs):
        global log
        log = logging.getLogger(inspect.stack()[1][3])
        log.info('About to run %s' % fn.__name__)

        out = fn(*args, **kwargs)

        log.info('Done running %s' % fn.__name__)
        # Return the return value
        return out
    return wrapper

    @app.route('/this_func')
    @logger
    def this_func():
        log.info('I am doing logging without having to do bunch of definitions.')
        # some more code

    @app.route('/that_func')
    @logger
    def that_func():
        log.info('Yet more logging without having to do bunch of definitions.')
        log.info('I can simply refer to the log object and be done with it.')
        # some more code

最佳答案

对我有用的最终设置如下:

# At the beginning of every .py file in the project
def logger(fn):
    from functools import wraps
    import inspect
    @wraps(fn)
    def wrapper(*args, **kwargs):
        log = logging.getLogger(fn.__name__)
        log.info('About to run %s' % fn.__name__)

        out = fn(*args, **kwargs)

        log.info('Done running %s' % fn.__name__)
        # Return the return value
        return out
    return wrapper

# Do the following section only in application's app/__init__.py
# Other files will pick it up from here.
FORMAT = '%(asctime)s - %(name)s - %(levelname)s - %(funcName)s - %(message)s'

# Change logging LEVEL according to debugging needs.
# Probably better to read this from a config or a launch parameter.
LEVEL = logging.DEBUG

logging.basicConfig(format=FORMAT, level=LEVEL)
# Up to here only for app/__init__.py

# This section again at the beginning of every .py file
log = logging.getLogger(__name__)
log.info('Entered module: %s' % __name__)

现在,为模块中的每个函数定义添加一个 @logger 装饰器:

@logger
def do_something():
    print('doing really useful stuff.')

关于python - 如何在 Python 中的函数入口、内部和导出处进行日志记录,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23435488/

相关文章:

logging - Storm-0.10.0 所有worker登录supervisor.log

python - 尝试向本地主机 :9000/store 发送错误时,Django-Sentry 给出错误 405

java - 使用 Logback 即时更改日志文件路径属性

python - KNN 查询数据维度必须与训练数据维度匹配

python - 检测 Django 函数是否正在 celery worker 中运行

java - RestAssured 外部文件日志记录

logging - 是否可以像 Eclipse 一样将控制台输出重定向到 IntelliJ 中的日志文件?

python - <django.db.models.fields.related.RelatedManager object at 0x7ff4e003d1d0> 不是 JSON 可序列化的

python - 如何获取 SymPy 表达式中的符号数

python - 以 django 形式强制