On Thu, Jan 31, 2013 at 1:56 AM, Nick Coghlan firstname.lastname@example.org wrote:
Looking at the problem from a different direction:
Currently, modules are *instances* of a normal type (types.ModuleType). Thus, anything stored in their global namespace is like anything else stored in a normal instance dictionary: no descriptor behaviour.
The request in this thread is basically for a way to:
- Define a custom type
- Put an instance of that type in sys.modules instead of the ordinary
Now here's the thing: we already support this, because the import system is designed to cope with modules replacing "sys.modules[__name__]" while they're being loaded. The way this happens is that, after we finish loading a module, we usually don't trust what the loader gave us. Instead, we go look at what's in sys.modules under the name being loaded.
So if, in your module code, you do this:
import sys, types class MyPropertyUsingModule(types.ModuleType): def __init__(self, original): # Keep a reference to the original module to avoid the # destructive cleanup of the global namespace self._original = original @property def myglobal(self): return theglobal @myglobal.setter def myglobal(self, value): global theglobal theglobal = value sys.modules[__name__] = MyPropertyUsingModule(sys.modules[__name__])
Then what you end up with in sys.modules is a module with a global property, "myglobal".
I'd prefer to upgrade this from "begrudged backwards compatibility hack" to "supported feature", rather than doing anything more complicated.
At this point I don't see this behavior of the import system changing, even for Python 4. Making it part of the spec is the best fit for this class of problem (not-terribly-sophisticated solution for a relatively uncommon case). Otherwise we'd need a way to allow a module definition (.py, etc.) to dictate which class to use, which seems unnecessary and even overly complicated given the scale of the target audience.
That said, Larry's original proposal relates to sys, a built-in module written in C (in CPython of course). In that case the solution is not quite the same, since module initialization interacts with sys.modules differently.  Accommodating the original request would require more work, whether to muck with the import C-API or making sys an instance of another type, as someone suggested.