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

通过pgBouncer从Prisma连接Supabase Postgres的连接池问题排查

问题分析与解决方案

核心问题判断

从你描述的现象(pgBouncer角色连接数为0、pg_stat_activity中显示容器IP)可以直接得出:你的应用完全绕过了pgBouncer,直接连接到了Postgres实例,这才导致连接随容器数量线性增长,最终耗尽。

正确使用pgBouncer的预期状态

1. pg_stat_activity 状态

  • 所有来自应用的连接,client_addr字段显示的是Supabase pgBouncer节点的IP(而非你的Cloud Run容器IP)
  • 连接的application_name可能会标记为pgBouncer,或保留应用自定义名称,但连接发起方为pgBouncer服务
  • 应用角色的连接数会被控制在pgBouncer的池大小范围内(Supabase根据套餐配置,比如免费版默认20),不会随容器数量暴涨

2. Supabase角色连接数

  • pgBouncer角色的连接数大于0,对应pgBouncer持有的到Postgres的实际物理连接数
  • 应用角色的连接数远小于Cloud Run容器数量(因为pgBouncer池化了连接,多个容器复用少量物理连接)

排查与修复步骤

1. 彻底校验连接字符串

确认DATABASE_URL完全符合要求:

  • 端口必须是6543(pgBouncer专属端口,而非Postgres默认的5432)
  • 必须包含pgbouncer=true参数
  • 完整格式示例:
    postgres://postgres:YOUR_PASSWORD@db.YOUR_PROJECT.supabase.co:6543/postgres?pgbouncer=true
    
  • 检查Cloud Run的环境变量配置,确保部署时没有误用5432端口的连接字符串

2. 调整Prisma连接池配置

在schema.prisma中合理设置连接池大小,避免单个容器的连接数过多:

datasource db {
  provider = "postgresql"
  url      = env("DATABASE_URL")
  pool_size = 3 // 根据容器数量和pgBouncer总连接数调整,比如10个容器的话,总连接数不要超过pgBouncer的上限
}

注意:所有容器的Prisma连接池总大小(pool_size × 容器数量)必须小于等于Supabase pgBouncer的最大连接数(可在Supabase「数据库>设置」中查看)

3. 生效配置并验证

  • 重启所有Cloud Run容器,确保新的连接字符串和池配置生效
  • 重新查询pg_stat_activity,确认client_addr变为pgBouncer节点IP
  • 查看Supabase「数据库>角色」页面,确认pgBouncer角色连接数大于0

4. 额外优化点

  • 避免长时持有连接:确保请求处理完成后立即释放连接(Prisma默认自动管理,但手动事务或长耗时查询需注意)
  • 若使用Prisma的事务操作,确保遵循pgBouncer的模式限制(Supabase默认使用session模式,兼容性较好;若切换为transaction模式,需避免使用SET等会话级语句)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 22:55:18