You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Azure无服务器函数应用中CosmosClient连接管理问题求助

问题

微软建议在整个应用中维护单个CosmosClient实例,我在Azure无服务器Python函数应用里尝试这么做(不止是CosmosClient),但就算复用数据库和容器代理,请求量一大就收到警告:已达Cosmos最大连接数(10个),正在丢弃连接。

背景:这是个由消息队列触发的无服务器Python函数应用,连接通过辅助函数里的共享代码管理,必须用Cosmos SDK来读写文档。

想问有没有人解决过这类问题?为每个函数调用实例化新连接是不是最佳实践?我试过在突发流量时创建新CosmosClient,但很难高效实现。

下面是我用来管理连接的类示例:

COSMOS_CLIENT = None

class Client:
    def __init__(self):
        self.cosmos_client: CosmosClient = self._get_global_cosmos_client()
    
    def _get_global_cosmos_client() -> CosmosClient:
        global COSMOS_CLIENT
        if COSMOS_CLIENT is None:
            logging.info('[COSMOS] NEW CLIENT CONNECTION')
            COSMOS_CLIENT = CosmosClient.from_connection_string(COSMOS_DB_CONNECTION_STRING)
        return COSMOS_CLIENT
解决方案
  • 绝对不要为每个函数调用实例化新连接:这会快速耗尽Cosmos的连接配额,反而加剧问题。单实例复用是正确方向,但要适配Azure函数的运行时特性。
  • 显式调整CosmosClient的连接池配置:默认配置可能不匹配无服务器场景,初始化时自定义连接策略参数:
    from azure.cosmos import CosmosClient, ConnectionPolicy
    
    def _get_global_cosmos_client() -> CosmosClient:
        global COSMOS_CLIENT
        if COSMOS_CLIENT is None:
            logging.info('[COSMOS] NEW CLIENT CONNECTION')
            policy = ConnectionPolicy()
            policy.max_connection_limit = 10  # 不要超过Cosmos账户的配额,可按需微调
            policy.idle_connection_timeout = 30  # 缩短空闲连接超时,快速释放闲置资源
            COSMOS_CLIENT = CosmosClient.from_connection_string(COSMOS_DB_CONNECTION_STRING, connection_policy=policy)
        return COSMOS_CLIENT
    
  • 复用数据库与容器代理实例:不要每次请求都重新获取数据库、容器对象,将它们也设为全局变量复用:
    COSMOS_CLIENT = None
    COSMOS_DB = None
    COSMOS_CONTAINER = None
    
    class Client:
        def __init__(self):
            self.cosmos_client = self._get_global_cosmos_client()
            self.db = self._get_global_db()
            self.container = self._get_global_container()
        
        def _get_global_cosmos_client() -> CosmosClient:
            global COSMOS_CLIENT
            if COSMOS_CLIENT is None:
                logging.info('[COSMOS] NEW CLIENT CONNECTION')
                policy = ConnectionPolicy()
                policy.max_connection_limit = 10
                policy.idle_connection_timeout = 30
                COSMOS_CLIENT = CosmosClient.from_connection_string(COSMOS_DB_CONNECTION_STRING, connection_policy=policy)
            return COSMOS_CLIENT
        
        def _get_global_db(self):
            global COSMOS_DB
            if COSMOS_DB is None:
                COSMOS_DB = self.cosmos_client.get_database_client(DATABASE_NAME)
            return COSMOS_DB
        
        def _get_global_container(self):
            global COSMOS_CONTAINER
            if COSMOS_CONTAINER is None:
                COSMOS_CONTAINER = self.db.get_container_client(CONTAINER_NAME)
            return COSMOS_CONTAINER
    
  • 接受Azure函数的横向扩展特性:当函数应用横向扩展出多个实例时,每个实例会持有自己的COSMOS_CLIENT,这是正常现象,每个实例的连接数独立计算,不会互相占用配额。
  • 排查连接泄漏:检查代码中是否有未正确收尾的操作,比如异步请求未处理完成、长期持有资源的逻辑,导致连接池无法回收连接。
  • 调整Cosmos账户配额(按需):如果业务确实需要更高连接数,可在Azure门户中调整Cosmos账户的连接配额,但这会带来额外成本。

内容的提问来源于stack exchange,提问作者Hunter Boyd

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 18:57:05