[Python-Dev] PEP 549: Instance Properties (aka: module properties)

Guido van Rossum guido at python.org
Mon Sep 11 11:44:36 EDT 2017


On Sun, Sep 10, 2017 at 8:52 PM, Larry Hastings <larry at hastings.org> wrote:
>
> On 09/06/2017 02:13 PM, Ronald Oussoren wrote:
>
> To be honest this sounds like a fairly crude hack. Updating the __class__
> of a module object feels dirty, but at least you get normal behavior w.r.t.
> properties.
>
> Okay.  Obviously I disagree, I think it's reasonable.  But I'll assume
> you're -1.
>

I'm still poindering this. I am far from decided about whether it's better
to just add @property support, or whether we should add __getattr__ instead
(it can do everything @property can do, plus other things, but the
@property support would be a little clumsier), or everything that a class
can do with attributes (e.g. __getattribute__, __dir__, __setattr__), or
leave things alone (__class__ assignment can solve everything).

I worry that in the end @property isn't general enough and the major use
cases end up still having to use __class__ assignment, and then we'd have a
fairly useless feature that we cant withdraw, ever.

> Why is there no mechanism to add new descriptors that can work in this
> context?
>
> I've updated the prototype to add one.  I added it as "collections.abc.InstanceDescriptor";
> that's a base class you can inherit from, and then your descriptor will
> work in a module.  Bikeshedding the name is fine.
>

I don't understand the question, or the answer. (And finding the prototype
is taking longer than writing this email.)

> BTW. The interaction with import is interesting… Module properties only
> work as naive users expect when accessing them as attributes of the module
> object, in particular importing the name using “from module import prop”
> would only call the property getter once and that may not be the intended
> behavior.
>
> I spent a fair amount of time thinking about this.  The short answer is:
> we *could* fix it.  We *could* make it so that "from x import y", when
> x.y is an instance descriptor, ensures that y honors the descriptor
> protocol when referenced.  We'd have to do it for three contexts:
>
>    - global scope (aka module scope)
>    - class scope
>    - function scope
>
> The first two are pretty similar; create a proxy object that retains the
> module instance so it remains "bound" to that.  The third one is trickier;
> it'd mean a new bytecode (LOAD_FAST_DESCRIPTOR), but it wouldn't slow down
> people who didn't use it.
>
> Anyway, long story short, I think this would be worse than simply having
> "from x import y" only calling the getter once.  As the Zen says: special
> cases aren't special enough to break the rules.
>

I agree -- let's please not fix this, it's way too complicated for
something that started out as a nice localized tweak. When we write "from x
import y" we already voluntarily give up seeing any later assignments to
x.y. If this prevents a certain use case for lazy import, then so be it --
I don't think lazy import can ever be made so transparent that everything
will work lazily without understanding the difference between lazy and
eager import. (People already have to understand many subtleties of import,
e.g. the difference between import and loading, and how circular imports
work.)

-- 
--Guido van Rossum (python.org/~guido)
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-dev/attachments/20170911/211f9000/attachment.html>


More information about the Python-Dev mailing list