Python 装饰器的典型使用场景(2)
来源:互联网 发布:恐怖童谣案件还原知乎 编辑:程序博客网 时间:2024/06/05 08:01
Python 装饰器的典型使用场景(2)
前一篇文章中(http://blog.csdn.net/qq_26886929/article/details/54091962),我们谈了装饰器的两方面用法,本文将讨论装饰器用作代理(Proxy)和上下文提供者(Context Provider)两个用途:
1. 代理(Proxy)装饰器
代理装饰器可被用作标记和注册函数的全局机制。例如,根据当前用户,保护对代码进行访问的安全层,可以使用一个关联着可调用对象所要求的权限的集中检测器来实现:
class User(object): def __init__(self, roles): self.roles = rolesclass Unauthorized(Exception): passdef protect(role): def _protect(function): def __protect(*args, **kw): user = globals().get('user') if user is None or role not in user.roles: raise Unauthorized("I won't tell you") return function(*args, **kw) return __protect return _protect
这种模式常常被用在 Python 网络框架中,来定义可发布类的安全。例如,Django 使用装饰器来提供函数访问的安全。
下面是个例子,在这个例子中当前用户被保存在一个全局变量中。当方法被调用时,装饰器会检查该用户的角色,以觉得该用户是否有访问权限:
>>> tarek = User(('admin', 'user'))>>> bill = User(('user',))>>> class MySecrets(object):... @protect('admin')... def waffle_recipe(self):... print('use tons of butter!')...>>> these_are = MySecrets()>>> user = tarek>>> these_are.waffle_recipe()use tons of butter!>>> user = bill>>> these_are.waffle_recipe()Traceback (most recent call last):File "<stdin>", line 1, in <module>File "<stdin>", line 7, in wrap__main__.Unauthorized: I won't tell you
2. 上下文提供者(Context Provider)
上下文装饰器被用来确保函数在正确的上下文环境运行,或者确保在函数运行前和运行后执行一些代码。换言之,该装饰器进行设置或取消设置某个特定的运行环境。例如,当一条数据要在多个线程之间共享时,就需要使用锁(lock)来确保数据被保护,以防出现并发访问。锁能够像下面这样放在装饰器中:
from threading import RLocklock = RLock()def synchronized(function): def _synchronized(*args, **kw): lock.acquire() try: return function(*args, **kw) finally: lock.release() return _synchronized@synchronizeddef thread_safe(): # make sure it locks the resource pass
上下文装饰器,通常被上下文管理器(with 语句)取代。
1 0
- Python 装饰器的典型使用场景(2)
- Python 装饰器的典型使用场景(1)
- python 函数装饰器的典型示例
- 【Python笔记】装饰器语法糖(@staticmethod/@classmethod/@property)原理剖析及使用场景说明
- python 装饰器的使用
- python装饰器的使用
- python 装饰器的使用
- python装饰器的使用
- python装饰器的使用
- spring schedule的几个典型使用场景
- RabbitMQ的几种典型使用场景
- Mysql中使用索引的典型场景
- RabbitMQ的几种典型使用场景
- RabbitMQ的几种典型使用场景
- RabbitMQ的几种典型使用场景
- RabbitMQ的几种典型使用场景
- RabbitMQ的几种典型使用场景
- RabbitMQ的几种典型使用场景
- UML依赖与关联,聚合和组合
- JavaWeb-3-web服务启动时加载类中的某个方法配置(Spring mvc模式下)
- js笔记二:node.js的npm使用理解
- 简易ajax天气渲染
- 提取数字、英文、中文、过滤重复字符等SQL函数(含判断字段是否有中文)
- Python 装饰器的典型使用场景(2)
- 1. 环境配置
- caffe的python接口学习(2):生成solver文件
- Zend Studio + Firefox调试PHP代码
- iOS app打包 -- 生成ipa测试包 步骤详解
- python的字符串操作
- java.io.File类中mkdir()与mkdirs()区别
- 今天使用JPA中的 findone()函数在一对多时发生查询数据重复
- 拿什么来衡量程序员的生产力?