python - 如何在 python 烧瓶应用程序中外部化装饰器
问题描述
我编写了一个 python Flask 应用程序,它有一个类和方法如下。
class PythonSample:
def method1():
pass # does something
def method2():
pass # does something
现在我编写了另一个具有如下装饰器功能的类。
class PythonAuth:
def oauthAuth():
pass
现在我正在为 PythonSample 类的所有方法连接 oauthAuth 装饰器,如下所示
import oauthAuth from PythonAuth
class PythonSample
@oauthAuth
def method1():
pass # does something
@oauthAuth
def method2():
pass # does something
在每种方法上应用装饰器都可以正常工作。
问题:而不是将 oauthAuth 装饰器应用于每个方法。有没有办法在 python 中配置,将 oauthAuth 装饰器应用于类中的所有方法并排除某些方法。
诸如包含某些 URL 的身份验证和排除某些 URL 的身份验证之类的东西
请忽略此处 python 代码的语法。
解决方案
You can use a class decorator plus some magic.
Decorating Functions
Assume you have a decorator that just logs a string before calling the function.
def log(func):
def logged_func(*args, **kwargs):
print('logged')
func(*args, **kwargs)
return logged_func
Decorating classes
You can use the same trick, but with a class. log_all
is a class decorator, cls
is a class type. We use vars
to walk the class dictionary, and look for methods by using callable(v)
. Decorate the method with log(v)
and use setattr
to change the cls
definition to the new decorated method. Just like function decorators, return the class in the end.
def log_all(cls):
for k, v in vars(cls).items():
if callable(v):
setattr(cls, k, log(v))
return cls
I am ignoring k
essentially, but k
is the method name, you could leverage it to achieve your usage scenario.
Full code
Here is a full example, that should make some sense now.
def log(func):
def logged_func(*args, **kwargs):
print('logged')
func(*args, **kwargs)
return logged_func
def log_all(cls):
for k, v in vars(cls).items():
if callable(v):
setattr(cls, k, log(v))
return cls
@log_all
class A:
def method(self):
pass
Every method in class A
should be decorated with the log
decorator.
>>> a = A()
>>> a.method()
logged
推荐阅读
- gerrit - 格里特无视詹金斯的反对票
- css - Pan/scroll image image inside a div container
- sql - 用过程替换触发器
- maven - 排除 AnnotationProcessorPaths 中的依赖项
- c# - 如何使用 automapper 9.0.0.0 根据句柄属性自动映射两个列表
- sql-server - 使用 Azure Data Lake Store Gen1 中的 SSIS 包将文件从一个目录移动到另一个目录
- wordpress - 仅删除单页上的 Yoast Breadcrumb 最后一项
- vba - 是否可以将先前代码生成的文件名用作下一行代码的变量?
- sql-server - 解析 SQL 脚本以查找表依赖项和输出
- javascript - 如何在某个属性设置为 false 的对象数组中找到下一个对象?