I"m trying to get the name of the Python script that is currently running.
I have a script called
foo.py and I"d like to do something like this in order to get the script name:
You can use
__file__ to get the name of the current file. When used in the main module, this is the name of the script that was originally invoked.
If you want to omit the directory part (which might be present), you can use
import sys print(sys.argv)
This will print
python dir/foo.py, etc. It"s the first argument to
python. (Note that after py2exe it would be
For completeness" sake, I thought it would be worthwhile summarizing the various possible outcomes and supplying references for the exact behaviour of each.
The answer is composed of four sections:
A list of different approaches that return the full path to the currently executing script.
A caveat regarding handling of relative paths.
A recommendation regarding handling of symbolic links.
An account of a few methods that could be used to extract the actual file name, with or without its suffix, from the full file path.
__file__ is the currently executing file, as detailed in the official documentation:
__file__is the pathname of the file from which the module was loaded, if it was loaded from a file. The
__file__attribute may be missing for certain types of modules, such as C modules that are statically linked into the interpreter; for extension modules loaded dynamically from a shared library, it is the pathname of the shared library file.
From Python3.4 onwards, per issue 18416,
__file__ is always an absolute path, unless the currently executing file is a script that has been executed directly (not via the interpreter with the
-m command line option) using a relative path.
__main__.__file__ (requires importing
__main__) simply accesses the aforementioned
__file__ attribute of the main module, e.g. of the script that was invoked from the command line.
sys.argv (requires importing
sys) is the script name that was invoked from the command line, and might be an absolute path, as detailed in the official documentation:
argvis the script name (it is operating system dependent whether this is a full pathname or not). If the command was executed using the
-ccommand line option to the interpreter,
argvis set to the string
"-c". If no script name was passed to the Python interpreter,
argvis the empty string.
As mentioned in another answer to this question, Python scripts that were converted into stand-alone executable programs via tools such as py2exe or PyInstaller might not display the desired result when using this approach (i.e.
sys.argv would hold the name of the executable rather than the name of the main Python file within that executable).
If none of the aforementioned options seem to work, probably due to an atypical execution process or an irregular import operation, the inspect module might prove useful. In particular, invoking
inspect.stack()[-1] should work, although it would raise an exception when running in an implementation without Python stack frame.
From Python3.6 onwards, and as detailed in another answer to this question, it"s possible to install an external open source library, lib_programname, which is tailored to provide a complete solution to this problem.
This library iterates through all of the approaches listed above until a valid path is returned. If all of them fail, it raises an exception. It also tries to address various pitfalls, such as invocations via the pytest framework or the pydoc module.
import lib_programname # this returns the fully resolved path to the launched python program path_to_program = lib_programname.get_path_executed_script() # type: pathlib.Path
When dealing with an approach that happens to return a relative path, it might be tempting to invoke various path manipulation functions, such as
os.path.realpath(...) in order to extract the full or real path.
However, these methods rely on the current path in order to derive the full path. Thus, if a program first changes the current working directory, for example via
os.chdir(...), and only then invokes these methods, they would return an incorrect path.
If the current script is a symbolic link, then all of the above would return the path of the symbolic link rather than the path of the real file and
os.path.realpath(...) should be invoked in order to extract the latter.
os.path.basename(...) may be invoked on any of the above in order to extract the actual file name and
os.path.splitext(...) may be invoked on the actual file name in order to truncate its suffix, as in
From Python 3.4 onwards, per PEP 428, the
PurePath class of the
pathlib module may be used as well on any of the above. Specifically,
pathlib.PurePath(...).name extracts the actual file name and
pathlib.PurePath(...).stem extracts the actual file name without its suffix.
The genesis of this book began in 2012. Hadoop was being explored in mainstream organizations, and we believed that information architecture was about to be transformed. For many years, business intel...
Why this Book? Hadoop has been the base for most of the emerging technologies in today’s big data world. It changed the face of distributed processing by using commodity hardware for large data set...
A Practical Approach to Computer Algorithms Using Python® and C# Rod Stephens started out as a mathematician, but while studying at MIT, he discovered how much fun algorithms are. He took every al...
Data is “unreasonably effective”. Nobel laureate Eugene Wigner referred to the unreasonable effectiveness of mathematics in the natural sciences. What is big data? Its sizes are in the order of te...