[Python-ideas] Replacing the if __name__ == "__main__" idiom (was Re: making a module callable)

Steven D'Aprano steve at pearwood.info
Sat Nov 23 05:06:09 CET 2013


On Fri, Nov 22, 2013 at 05:45:22PM -0800, Sean McQuillan wrote:
> Adding a mainfunction decorator was mentioned in the other thread, seemed
> interesting so I coded up a simple example to see how it works.
> 
> https://github.com/objcode/mainfunction/blob/master/mainfunction/mainfunction.py

I haven't actually tried it, but by reading the code I don't think that 
works the way I expect a main function to work. Your decorator simply 
does a bit of book-keeping, then immediately calls the main function. So 
it doesn't so much define a main function as just execute it straight 
away, which means it works with simple cases like this:


@mainfunction
def main():
    print "Hello, World."


but not for cases like this:


@mainfunction
def main():
    do_stuff("Hello, World!")

def do_stuff(msg):
    print msg


since do_stuff doesn't exist at the time main() is executed. In 
contrast, the standard idiom is typically the very last thing at the 
bottom of the file, and so by the time it is called all the support 
functions are in place.

My aesthetic sense tells me that there are two reasonable approaches 
here:

1) The current idiom, with an explicit "if __name__" test. This is the 
most flexible.

2) An implicit main function, which I think should be spelled __main__ 
to emphasise that it is special. This, I think, would require support 
from the compiler. (At least, I can't see any easy way to bootstrap it 
without using the "if __name__" test above.)

python some_file.py

python -m some_file

would both execute the file as normal. The only addition would be, after 
the file has been run the compiler checks whether there is a name 
"__main__" in the global namespace, and if so, calls that __main__ 
object with sys.argv as argument.

This second is analogous to the situation with packages. If a package 
has a __main__.py file, it is run when you call

python -m package


This second approach is purely a convenience for writing scripts, it 
doesn't given you anything you can't already do with the current idiom, 
but I think that defining a special main function

def __main__(argv):
    ...


is a cleaner (but less flexible) idiom that the current if __name__ 
business, and simpler for people to learn.


-- 
Steven


More information about the Python-ideas mailing list