在类中创建一个装饰器调用特定于方法的pre和post方法

时间:2015-08-17 19:21:34

标签: python decorator introspection python-decorators

在python 3中,我有一个基类,派生一个类:

class Base:
    # Tell the Base class to look and for pre/post 
    # functions the same name, and call them
    def f(self):
        print("f()")

    def no_prepost(self): # should work, too
        print("nothing")

class Derived(Base):
    def pre_f(self):
        print("pre_f()")

    def post_f(self):
        print("post_f()")

我想调用前/后方法,如果它们存在,但没有明确说明它们:

foo = Derived()

# if exists: foo.pre_f() -- too verbose, do this automatically!
foo.f()
# if exists: foo.post_f()

1 个答案:

答案 0 :(得分:1)

装饰器功能和一些类内省可以做到这一点。如果找到匹配函数,则使用相同的参数调用它:

def prepost(f):
    def prepost_wrapper(self, *args, **kwargs):
        pre_name  = 'pre_'  + f.__name__
        post_name = 'post_' + f.__name__
        if hasattr(self, pre_name):  getattr(self, pre_name) (*args, **kwargs)
        ret = f(self, *args, **kwargs)
        if hasattr(self, post_name): getattr(self, post_name)(*args, **kwargs)
        return ret
    return prepost_wrapper

class Base:
    @prepost    
    def f(self, a, b=99):
        print("f()", a, b)
    @prepost
    def missing(self):
        print("nothing special here")

class Derived(Base):
    def pre_f(self, a, b=0): # the arguments must match!
        print("pre_f()", a, b)
    def post_f(self, a, b=1):
        print("post_f()", a, b)

foo = Derived()
foo.f("abc")
foo.missing()
foo.f("xyz", 12)

输出:

pre_f() abc 0
f() abc 99
post_f() abc 1
nothing special here
pre_f() xyz 12
f() xyz 12
post_f() xyz 12