python 设计模式(十一) 代理模式(Proxy pattern)

    代理模式在日常生活中很常见,比如,你去杂货店买一个插座,而不是去生产插座的工厂去买。再比如,你去访问某个网站,你并没有访问权限,但你可以通过代理去访问这个网站,然后代理再把内容传给你。讲代理模式之前,先讲下正向代理和反向代理的区别:

正向代理

上面访问网站的例子就是正向代理,可以用下面的流程图展示这一机制。

python 设计模式(十一) 代理模式(Proxy pattern)_第1张图片

正向代理:客户端访问某网站,先访问代理,代理去访问某网站,然后把内容返回给客户端,这就是正向代理。正向代理就是我们现实中常用的代理模式。杂货店代理工厂的产品,火车票代售点代理火车票业务等等。

反向代理

如下图

python 设计模式(十一) 代理模式(Proxy pattern)_第2张图片

反向代理:客户端去访问某个网站的某个资源,但这个网站没有这个资源,同时这个网站被设置为反向代理,那么这个网站就会从其他服务器上获取这个资源返回给客户端。因此客户端并不知道这个资源是谁提供的,它只要知道代理网站的网站即可。比如我们访问百度,背后有成千上万的反向代理服务器在为我们服务,但我们只要知道baid.com这个网站就行了,不必知道访问的资料具体来自哪里。nginx是高流量web服务器流行选择,它支持反向代理和负载均衡。

代理模式

代理模式就是给对象提供一个代理,用来控制对对象的访问。比如,对于网站中用户经常访问的资源,可以用redis数据库进行存储,以加快网站响应速度。下面实现了网站对常用资源访问设置缓存的设计。

Source类是网站常用资源,source_proxy是常用资源的代理类,client是客户端,cache类存储了常用的访问资源。具体实现如下代码


# author guoyibo
class Cache(object):
    """
    use for save source that ofen is requested
    """
    def __init__(self):
        self.cache = {}

    def get(self, key):
        return self.cache.get(key)

    def set(self, key, value):
        self.cache[key] = value
        print('set %s to %s' % (value, key))

cache = Cache()


class Souce(object):
    def __init__(self, name):
        self.name = name

    @property
    def obtain(self):
        print('get source from source')
        return 'source of %s' % self.name


class Source_proxy(object):
    def __init__(self, source):
        self.source = source

    @property
    def obtain(self):
        content = cache.get(self.source.name)

        if not content:
            content = self.source.obtain
            cache.set(self.source.name, content)
        else:
            print('get source from cache')
        return content


class Client(object):

    def __init__(self, source):
        self.source = source

    def show(self):
        print('from backend get source %s' % self.source.obtain)


if __name__ == '__main__':
    source = Souce('picture.jpg')
    proxy = Source_proxy(source)
    # first visit
    client = Client(proxy)
    client.show()
    # second visit
    print('*'*20)
    client.show()

结果如下

get source from source
set source of picture.jpg to picture.jpg
from backend get source source of picture.jpg
********************
get source from cache
from backend get source source of picture.jpg

你可能感兴趣的:(python,python,设计模式)