web-dev-qa-db-ja.com

装飾された関数の名前を取得しますか?

これが私のデコレータです:

def check_domain(func):

    def wrapper(domain_id, *args, **kwargs):
        domain = get_object_or_None(Domain, id=domain_id)
        if not domain:
            return None
        return func(domain_id, *args, **kwargs)

    return wrapper

まとめた関数は次のとおりです。

@check_domain
def collect_data(domain_id, from_date, to_date):
    do_stuff(...)

collect_data.__name__を実行すると、collect_dataの代わりにwrapperが取得されます

何かアイデアはありますか?

27
RadiantHex

wraps from functoolsを使用することをお勧めします。

あなたに合っていると思われる明確な例があります:)

16

functools.wrapsは必要ありません! method.__name__を使用するだけです

import time

def timeit(method):
    def timed(*args, **kw):
        ts = time.time()
        result = method(*args, **kw)
        te = time.time()
        print('Function', method.__name__, 'time:', round((te -ts)*1000,1), 'ms')
        print()
        return result
    return timed

@timeit
def math_harder():
    [x**(x%17)^x%17 for x in range(1,5555)]
math_harder()

@timeit
def sleeper_agent():
    time.sleep(1)
sleeper_agent()

出力:

Function math_harder time: 8.4 ms
Function sleeper_agent time: 1003.7 ms
36
Zach Estela

に加えて functools.wraps、この問題を解決するために設計された デコレータ モジュールを確認できます。

4
tkerwin

チェックアウト functools.wraps 。それが問題である場合は、python 2.5以上が必要です。

3
meshantz
2

次のような複数のデコレータがある場合に、装飾された関数名にアクセスする必要がある人のために:

@decorator1
@decorator2
@decorator3
def decorated_func(stuff):
    return stuff

functools.wraps上記はそれを解決します。

1
Zevgon