On Aug 5, 1:16 pm, Duncan Booth <duncan.bo...@invalid.invalid> wrote: > Ryan <heni...@yahoo.com> wrote: > > In the context of descriptors, the __set__ method is not called for > > class attribute access. __set__ is only > > called to set the attribute on an instance instance of the owner class > > to a new value, value. WHY? Is there some other mechanism for > > accomplishing this outcome. This subtle difference from __get__cost me > > some time to track down. Might think about pointing that out the > > documentation. > > > class RevealAccess(object): > > """A data descriptor that sets and returns values > > normally and prints a message logging their access. > > """ > > > def __init__(self, initval=None, name='var'): > > self.val = initval > > self.name = name > > > def __get__(self, obj, objtype): > > print 'Retrieving', self.name > > return self.val > > > def __set__(self, obj, val): > > print 'Updating' , self.name > > self.val = val > > > class MyClass(object): > > x = RevealAccess(10, 'var "x"') > > y = 5 > > > print MyClass.x > > MyClass.x = 20 > > print MyClass.x > > MyClass.x = 30 > > print MyClass.x > > > Retrieving var "x" > > 10 > > 20 > > 30 > > > I am at a lost on how to intercept class attribute sets. Can anyone > > help :-/ > > The descriptor protocol only works when a value is being accessed or set > on an instance and there is no instance attribute of that name so the > value is fetched from the underlying class. >
That's not true. Properties, for example, can be got or set even when they shadow an instance attribute. You're (probably) thinking of __getattr__ which isn't invoked when an instance attribute exists. Also, the descriptor protocol *is* invoked for getting an attribute from a class - but not when setting a class attribute. An unfortunate asymmetry. It just wasn't considered as a use case when the descriptor protocol was implemented. Michael -- http://voidspace.org.uk/ -- http://mail.python.org/mailman/listinfo/python-list