Using descriptors to wrap methods

E

Edward C. Jones

Here is a stripped-down version of a Python Cookbook recipe. Is there a
simpler, more Pythonical, natural way of doing this?

------
#! /usr/bin/env python

# Modified from Python Cookbook entry 91192, "eiffelmethod" by Andres
# Tuells. The url is
# http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/91192

class MethodWraper(object):
def __init__(self, method):
self.method = method
def __get__(self, inst, type=None):
result = wrapper(inst, self.method)
setattr(inst, self.method.__name__, result)
return result

class wrapper:
def __init__(self, inst, method):
self.instance = inst
self.method = method

def __call__(self, *args, **kargs):
print 'pre'
result = apply(self.method, (self.instance,) + args, kargs)
print 'post'
return result

def test():
class C:
def f(self, arg):
print 'in f'
return arg+1
f = MethodWraper(f)

c = C()
print c.f(1)

if __name__=='__main__':
test()
------
 
D

Duncan Booth

Here is a stripped-down version of a Python Cookbook recipe. Is there a
simpler, more Pythonical, natural way of doing this?

Here's a simpler way of doing the same thing:
def wrapper(self, *args, **kw):
print 'pre'
result = f(self, *args, **kw)
print 'post'
return result
return wrapper
def f(self, arg):
print 'in f'
return arg+1
f = MethodWrapper(f)

pre
in f
post
2
Or if you want pre and post code customisable you might try:
def wrapper(self, *args, **kw):
if pre: pre(self, *args, **kw)
result = f(self, *args, **kw)
if post: post(self, result, *args, **kw)
return result
return wrapper
def pre_f(self, arg):
print 'pre',arg
def post_f(self, res, arg):
print 'post',res,arg
def f(self, arg):
print 'in f'
return arg+1
f = MethodWrapper(f, pre_f, post_f)


pre 1
in f
post 2 1
2
I don't know if you could call it Pythonic though.
 
S

Sean Ross

Edward C. Jones said:
Here is a stripped-down version of a Python Cookbook recipe. Is there a
simpler, more Pythonical, natural way of doing this?

def wrap(f):
def wrapped(*args, **kwds):
print 'pre'
result = f(*args, **kwds)
print 'post'
return result
return wrapped
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,007
Latest member
obedient dusk

Latest Threads

Top