[Python-ideas] Making it easy to prepare for PEP479

Chris Angelico rosuav at gmail.com
Mon May 18 16:13:21 CEST 2015


On Mon, May 18, 2015 at 11:32 PM, Joao S. O. Bueno
<jsbueno at python.org.br> wrote:
> Indeed - importing as NOP would surely be broken -
>
> The nice fix would be to be able to do
> from __future__ import jaberwock
>
> and have a plain "ImportError" that could be catched.

Indeed. Though I'm not sure what a correctly-spelled "from __future__
import jabberwock" would do; exceptions already "burble" up the call
stack until they meet "the clause that catch[es]" them. :)

> But, as Chris Angelico put it, it might be complicated.
> Manually testing sys.version seens to be the way to go
> Because,  even if making __future__ imports raise
> ImportError, taht would also only be available from
> Py 3.5/3.6 onwards.
>
> (Otherwise
> from __future__ import from__future__import_ImportError
> seens fun enough to actually be created)

Heh. Though there's no particular reason to guard this with a future
directive; if the behaviour were to be changed, it could just be done
immediately - you wouldn't need a couple of minor versions' notice
that something's going to stop raising errors.

The way to make this work would be two-fold. Firstly, an incorrect
__future__ directive would have to no longer be a SyntaxError; and
secondly, __future__ directives would have to be permitted after a try
statement (currently, they're not allowed to follow anything, so the
'try' would have to be special-cased to be allowed in). With those two
changes, though, the failing of a __future__ directive would now
become a failure at the (usually-ignored) run-time import - the
regular action of "from module import name" would fail when it tries
to import something that isn't present in the module. As a side
effect, some specific directives would become legal no-ops:

from __future__ import CO_FUTURE_PRINT_FUNCTION
from __future__ import __builtins__
# etc

I don't see this as a problem, given that the point of the SyntaxError
is to catch either outright spelling errors or version issues (eg
trying to use "from __future__ import print_function" in Python 2.5),
both of which will still raise ImportError.

The question is, how often is it actually useful to import a module
and ignore a __future__ directive? Going through all_feature_names:

nested_scopes: No idea; I think code is legal with or without it.
generators: Using "yield" as a keyword will fail
division: Yes, this one would work
absolute_import: This would work
with_statement: Any actual use of 'with' will bomb out
print_function: Might work if you restrict yourself
unicode_literals: Possibly would work, but ow, big confusion
barry_as_FLUFL: No idea, give it a try!
generator_stop: Yes, would work.

So three of them would definitely work (in the sense that code is
syntactically correct in both forms), and you could cope in some way
with an except block; print_function would work as long as you build
your code with that in mind (but if you're doing that anyway, just
drop the future directive); and unicode_literals *might* work, maybe.
The rest? If you're using the future directive, it's because you want
the new keyword, which means you're going to be using it. If the
future directive isn't recognized, you're getting syntax errors
elsewhere, so there's no opportunity to try/except the problem away.
What will the future of Python future directives be like? Most likely
a similarly mixed bag, so this is a feature that could potentially
have very little value.

Is it worth downgrading an instant SyntaxError to a run-time
ImportError to allow a narrow use-case?

ChrisA


More information about the Python-ideas mailing list