Logging: Formatter: name of the function

Bengt Richter bokr at oz.net
Fri Dec 23 11:50:13 EST 2005


On Fri, 23 Dec 2005 16:23:57 +0100, Gregor Horvath <g.horvath at gmx.at> wrote:

>Hi,
>
>Is there a possibility to format a log message to give the function name 
>where the log appears?
>
>Example
>
>import logging
>
>def aTestFunction():
>   logger.debug("This is a message")
>
>The log should read:
>
>aTestFunction  This is a message.
>
>There is a possibilty to format the module namewith %(module)s, but I 
>did not find one for the function name.
>
>Is there a possibilty or can I create it myself?
>How can I determine the function name within a function?
>Introspection?
>
There's not a nice way that I know of, but you can do something like

 >>> import sys
 >>> def foo():
 ...     print 'logger string containing function name "%s"'%sys._getframe().f_code.co_name
 ...
 >>> foo()
 logger string containing function name "foo"

However, you might want to consider using a decorator that could
wrap a function if debugging and leave it alone otherwise. Also you
can log before and after calling the function. E.g.,

 >>> def debugdeco(f):
 ...     if not __debug__: return f
 ...     def wrap(*args, **kw):
 ...         print 'before entering function "%s" ...'%f.func_name
 ...         result = f(*args, **kw)
 ...         print 'after returning from function "%s" ...'%f.func_name
 ...         return result
 ...     wrap.func_name = f.func_name # make it look the same if desired
 ...     return wrap
 ...
 >>> @debugdeco
 ... def foo(something): print something; return 'whatever'
 ...
 >>> foo('hello')
 before entering function "foo" ...
 hello
 after returning from function "foo" ...
 'whatever'
 >>> __debug__ = False
   File "<stdin>", line 1
 SyntaxError: can not assign to __debug__

Oops, can't experiment that way ;-)
 >>> ^Z

We'll just start it with -O to set __debug__ False:
 
 [ 8:45] E:\Info\Politics>py24 -O
 Python 2.4b1 (#56, Nov  3 2004, 01:47:27)
 [GCC 3.2.3 (mingw special 20030504-1)] on win32
 Type "help", "copyright", "credits" or "license" for more information.
 >>> def debugdeco(f):
 ...     if not __debug__: return f
 ...     def wrap(*args, **kw):
 ...         print 'before entering function "%s" ...'%f.func_name
 ...         result = f(*args, **kw)
 ...         print 'after returning from function "%s" ...'%f.func_name
 ...         return result
 ...     wrap.func_name = f.func_name # make it look the same if desired
 ...     return wrap
 ...
 >>> @debugdeco
 ... def foo(something): print something; return 'whatever'
 ...
 >>> foo('hello')
 hello
 'whatever'

You could still do stuff unconditionally of course, and also inside foo.

Regards,
Bengt Richter



More information about the Python-list mailing list