On Tue, Mar 08, 2016 at 03:54:41AM +1100, Chris Angelico wrote:
Every once in a while, the issue pops up again of "import X" picking up X.py from the current directory, when a stdlib or pip-installed module named X was wanted.
Couldn't we (almost) fix that in an almost backwards-compatible way by moving the current directory to the end of the path, instead of the beginning?
If none of the modules in the current directory shadow the standard library, then you won't notice any difference.
If you are shadowing the standard library, then you're either doing it deliberately, which I expect will be rare, or it's an accident. If it's deliberate, then you probably know what you're doing and can work around the change of behaviour.
If it is an accident, then the standard library will shadow your module, rather than the other way around, which strikes me as better. (E.g. you won't accidently break IDLE by shadowing something IDLE depends on.)
Python almost has a mechanism for protecting against this, in the form of explicit package relative imports; the only problem is that the current directory isn't a package.
We shouldn't be talking about "current directory", since that's only relevant when you run Python without specifying a script to run. It is actually the directory containing the script being executed, not the current directory, which gets added to the path. If there is no script, the faux path '' is added to the path, and that gets treated as if it were '.' (the current directory).
So the solution is to treat the current directory as a pseudo-package. It'd be a backward-incompatible change, so it would need to be explicitly invoked. Something like:
python3 -p somefile.py
which would pretend to create an __init__.py in the current directory, change to the parent, and "from dirname import somefile".
Seems awfully convoluted and hard to understand.
How will it interact with running real packages? How about running modules using -m?
Even if it works, it relies on the user being knowledgeable enough to run `python3 -p script` instead of `python3 script`, which means the people who most need this new feature are the least likely to use it. I think that's the fatal objection to this: if the user knows enough to run -p, she knows enough to diagnose an accidental shadowing.
Idle could be protected from accidentally importing someone's "html.py", because "import html" shouldn't ever import from the current directory.
That won't help when the user runs
(well perhaps it will help *specifically* with IDLE, but not with the general problem of accidental shadowing).