getattr() woes
David M. Cooke
cookedm+news at physics.mcmaster.ca
Wed Dec 29 00:07:45 EST 2004
aahz at pythoncraft.com (Aahz) writes:
> In article <87hdm5hnet.fsf at thomas.local>,
> Thomas Rast <foo.bar at freesurf.ch.invalid> wrote:
>>
>>class dispatcher:
>> # ...
>> def __getattr__(self, attr):
>> return getattr(self.socket, attr)
>>
>>>>> import asyncore
>>>>> class Peer(asyncore.dispatcher):
>>... def _get_foo(self):
>>... # caused by a bug, several stack levels deeper
>>... raise AttributeError('hidden!')
>>... foo = property(_get_foo)
>>...
>
> You're not supposed to use properties with classic classes.
Even if dispatcher was a new-style class, you still get the same
behaviour (or misbehaviour) -- Peer().foo still raises AttributeError
with the wrong message.
A simple workaround is to put a try ... except AttributeError block in
his _get_foo(), which would re-raise with a different error that
wouldn't be caught by getattr. You could even write a property
replacement for that:
>>> class HiddenAttributeError(Exception):
... pass
>>> def robustprop(fget):
... def wrapped_fget(self):
... try:
... return fget(self)
... except AttributeError, e:
... raise HiddenAttributeError(*e.args)
... return property(fget=wrapped_fget)
Ideally, I think the better way is if getattr, when raising
AttributeError, somehow reused the old traceback (which would point
out the original problem). I don't know how to do that, though.
--
|>|\/|<
/--------------------------------------------------------------------------\
|David M. Cooke
|cookedm(at)physics(dot)mcmaster(dot)ca
More information about the Python-list
mailing list