Jolly

解读contextvars,在异步环境下生成全局的redis连接
最近解决了公司里一个爬虫项目的问题,也就是如何保持全局的redis连接。先来回想下问题如何,首先爬虫项目是用asy...
扫描右侧二维码阅读全文
07
2021/04

解读contextvars,在异步环境下生成全局的redis连接

最近解决了公司里一个爬虫项目的问题,也就是如何保持全局的redis连接。先来回想下问题如何,首先爬虫项目是用asyncio驱动,异步爬取数据,而redis连接用的是aioredis,难就难在,已有的代码,将redis连接池的异步创建放在了task里,而task里面又在不断的循环执行任务,这样就导致每循环一次,redis连接池就创建一遍,导致系统资源的极度浪费。
常规方法的直接引入是没用的,因为这是异步的环境。
那什么是contextvars
contextvars 来源于 PEP-567 ,它提供了 APIs 允许开发者去保存,访问及管理 local context。 它与 thread-local storage (TLS) 类似。但它还支持维护异步代码的 context.

这里直接上代码:

编写上下文部分

from contextvars import ContextVar, Context
from utils.redis import Redis

redis_client = ContextVar("redis_client")

class RedisGlobal:
    def __init__(self, code, level_db):
        self.DB_CODE = code
        self.REDIS_LEVEL_DB = level_db


    async def run(self):

        redis = Redis()

        try:
            test_redis = await redis.get_redis_pool((self.REDIS_LEVEL_DB, REDIS_PORT), password=REDIS_PASSWORD,db=0, encoding='utf-8')
           
        except Exception as e:
            pass

        redis_dict = {"test_redis": test_redis ,
                      }
        redis_client.set(redis_dict)
        return redis_client

调用部分

redis_global = RedisGlobal(CODE, LEVEL_DB)
redis_client = await redis_global.run()
redis_dict = redis_client.get()

然后就从字典里获取到连接了,这里的字典里也可以存多个链接。这样就实现了全局统一的redis连接。

Last modification:May 6th, 2021 at 12:20 pm
如果觉得我的文章对你有用,请随意赞赏

Leave a Comment

🌓