Python Changing name of method

3.2k Views Asked by At

Using python 3.6. I'm trying to write some code that will allow me to to place a unique identifier on class methods.

Here's an example:

def test(func):
    def wrap():
        pass
    wrap.__name__ += '_TEST'
    return wrap

class example:
    @test
    def method(self):pass

Console:

import inspect
Bar = example()
inspect.getmembers(Bar, predicate=inspect.ismethod)
Out[3]: 
[('method', # Name didn't change 
<bound method test.<locals>.wrap of <__main__.example object at 
0x000002670E073EF0>>)]
Bar.method.__name__
Out[4]: 'wrap_TEST'

I want to be able to loop over methods of a class and only execute the ones I have marked with my decorator. Can this be done?

2

There are 2 best solutions below

0
On BEST ANSWER

You could use a boolean flag to mark the functions. Here is my suggestion:

import inspect

def mark(func):
    func.flag = True
    return func

class C:
    @mark
    def a(self):
        pass

    @mark
    def b(self):
        pass

    def c(self):
        pass

methods = [m for n, m in inspect.getmembers(C) if hasattr(m, 'flag')]
print([m.__name__ for m in methods]) #=> ['a', 'b']
1
On

Rather than trying to change the name of the methods you have created, you can use the fact that functions and methods are first class objects to assign a property to the method itself.

In the following code, you can create a simple decorator that adds the property TEST to the methods you want to test.

def test(func):
    func.TEST = True
    return func


class example:
    @test
    def method(self):
        pass

ex = example()
ex.method.TEST
# returns:
True