天天看點

Python 中實作裝飾器時使用 @functools.wraps 的理由

Python 中使用裝飾器對在運作期對函數進行一些外部功能的擴充。但是在使用過程中,由于裝飾器的加入導緻解釋器認為函數本身發生了改變,在某些情況下——比如測試時——會導緻一些問題。Python 通過

functool.wraps

為我們解決了這個問題:在編寫裝飾器時,在實作前加入

@functools.wraps(func)

可以保證裝飾器不會對被裝飾函數造成影響。比如,在 Flask 中,我們要自己重寫

login_required

裝飾器,但不想影響被裝飾器裝飾的方法,則

login_required

裝飾器本身可以寫成下面的樣子:

def login_required_(func):
    @wraps(func)
    def decorated_view(*args, **kwargs):
        if current_app.login_manager._login_disabled:
            return func(*args, **kwargs)
        elif not current_user.is_authenticated:
            # return current_app.login_manager.unauthorized()
            return redirect(url_for("login.loginPage", next=request.url))
        return func(*args, **kwargs)

    return decorated_view