Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Get __name__ of calling function's module in Python

People also ask

What is __ name __ used for in Python?

The __name__ variable (two underscores before and after) is a special Python variable. It gets its value depending on how we execute the containing script. Sometimes you write a script with functions that might be useful in other scripts as well. In Python, you can import that script as a module in another script.

What will be the value of __ name __ attribute of the imported module?

The value of __name__ attribute is set to “__main__” when module is run as main program. Otherwise, the value of __name__ is set to contain the name of the module. We use if __name__ == “__main__” block to prevent (certain) code from being run when the module is imported.

What is __ module __ Python?

The __module__ property is intended for retrieving the module where the function was defined, either to read the source code or sometimes to re-import it in a script.


Check out the inspect module:

inspect.stack() will return the stack information.

Inside a function, inspect.stack()[1] will return your caller's stack. From there, you can get more information about the caller's function name, module, etc.

See the docs for details:

http://docs.python.org/library/inspect.html

Also, Doug Hellmann has a nice writeup of the inspect module in his PyMOTW series:

http://pymotw.com/2/inspect/index.html#module-inspect

EDIT: Here's some code which does what you want, I think:

import inspect 

def info(msg):
    frm = inspect.stack()[1]
    mod = inspect.getmodule(frm[0])
    print '[%s] %s' % (mod.__name__, msg)

Confronted with a similar problem, I have found that sys._current_frames() from the sys module contains interesting information that can help you, without the need to import inspect, at least in specific use cases.

>>> sys._current_frames()
{4052: <frame object at 0x03200C98>}

You can then "move up" using f_back :

>>> f = sys._current_frames().values()[0]
>>> # for python3: f = list(sys._current_frames().values())[0]

>>> print f.f_back.f_globals['__file__']
'/base/data/home/apps/apricot/1.6456165165151/caller.py'

>>> print f.f_back.f_globals['__name__']
'__main__'

For the filename you can also use f.f_back.f_code.co_filename, as suggested by Mark Roddy above. I am not sure of the limits and caveats of this method (multiple threads will most likely be a problem) but I intend to use it in my case.


I don't recommend do this, but you can accomplish your goal with the following method:

def caller_name():
    frame=inspect.currentframe()
    frame=frame.f_back.f_back
    code=frame.f_code
    return code.co_filename

Then update your existing method as follows:

def info(msg):
    caller = caller_name()
    print '[%s] %s' % (caller, msg)