Hi All,

Maybe this should be over in python-ideas, since there is a proposal down the bottom of this message. But first the background...

I've just wasted a silly amount of time debugging an issue that really I know about, but had forgotten.

I have a number of modules which include a main() function, and down the bottom this code:

 if __name__ == '__main__':
   sys.exit(main(sys.argv))

so that I have a convenient command line tool if I invoke the module directly. I typically have tiny shell wrappers like this:

 #!/bin/sh
 exec python -m cs.app.maildb -- ${1+"$@"}

In short, invoke this module as a main program, passing in the command line arguments. Very useful.

My problem?

When invoked this way, the module cs.app.maildb that is being executed is actually the module named "__main__". If some other piece of code imports "cs.app.maildb" they get a _different_ instance of the module. In the same program! And how did it cause me trouble? I am monkey patching my module for debug purposes, and that monkey patcher imports the module by name. So I was monkey patching cs.app.maildb, and _not_ patching __main__. And thus not seeing any effect from the patch.

I realise that having __name__ == '__main__' at all almost implies this effect. I am not sure it needs to.

The Proposal:

What are the implications of modifying the python invocation:

 python -m cs.app.maildb

to effectively do this (Python pseudo code):

 M = importlib.import("cs.app.maildb")
 M.__name__ = '__main__'
 sys.modules['__main__'] = M

i.e. import the module by name, but bind it to _both_ "cs.app.maildb" and "__main__" in sys.modules. And of course hack .__name__ to support the standard boilerplate.

This would save some confusion when the module is invoked from the python command line and also imported by the code; it is not intuitive that those two things give you distinct module instances.

Aside from the module's .__name__ being '__main__' even when accessed by the code as cs.app.maildb, are there other implications to such a change that would break real world code?

Cheers,
Cameron Simpson <c...@zip.com.au>

The reasonable man adapts himself to the world; the unreasonable one persists
in trying to adapt the world to himself.  Therefore all progress depends
on the unreasonable man.        - George Bernard Shaw
--
https://mail.python.org/mailman/listinfo/python-list

Reply via email to