Decorating class member functions

Rhamphoryncus rhamph at gmail.com
Fri May 4 13:19:32 EDT 2007


On May 3, 10:34 pm, Peter Otten <__pete... at web.de> wrote:
> The problem is not that you are decorating a method but that you are trying
> to use a callable class instance as a method. For that to work the class
> has to implement the descriptor protocol, see
>
> http://users.rcn.com/python/download/Descriptor.htm
>
> class Bugger (object):
>     def __init__ (self, module, fn, instance=None):
>         self.module = module
>         self.fn = fn
>         self.instance = instance
>
>     def __call__ (self, *args, **kws):
>         print "calling %s.%s()" % (self.module, self.fn.__name__)
>         if self.instance is not None:
>             args = (self.instance,) + args
>         ret_val = self.fn(*args, **kws)
>         return ret_val
>
>     def __get__(self, instance, class_):
>         if instance is None:
>             return self
>         return Bugger(self.module, self.fn, instance)
>
> def instrument (module_name):
>     ret_val = lambda x: Bugger(module_name, x)
>     return ret_val
>
> class Stupid(object):
>     @instrument("xpd.spam")
>     def update(self):
>         print "update()"
>
> s = Stupid()
> s.update()
> Stupid.update(s)

I've been bitten by the "class instances as decorators won't get
bound" bug many times.  I had no idea there was a direct solution.
Thanks!

--
Adam Olsen, aka Rhamphoryncus




More information about the Python-list mailing list