pgbouncer相关概念和使用
pgbouncer相关概念和使用
1.pgbouncer介绍
PG 是多进程结构,每新增一个会话就会新增一个进程,相对而言对数据库的开销就会比较巨大。
因为在正常业务会话中,有不少session 都有长时间的 idle的状态,而这个状态导致,此时如果需要连接,就需要建立新的进程,来访问数据库,那么连接数就上来了. 而使用pgbouncer的主要原因
PGBrouncer能够缓存和PostgreSQL的连接,当有连接请求进来的时候,直接分配pgbouncer与postgresql之间的空闲连接去执行,而不需要PostgreSQL fork出新进程来建立连接,以节省创建新进程,创建连接的资源消耗。
关键的是pgbouncer是使用libevent进行socket通信,通信效率高。每个连接仅消耗2kB内存。相对pg自身动辄 4MB 的work_mem算是很轻量级了。
如果要用大白话来说,没有使用pgbouncer的连接方式是私家车,如果车子太多,则路就塞满了,而使用了pgbouncer 的方式则类似公交车或小巴, 有人上车有人下车,座位是固定的,所以公交车如果本身有30个座位,但实际上在整个的路途中可不是仅仅支持30个人,至于支持了多少人,那就看连接到数据库的事务执行的快慢,是否能对一个连接进行复用, 这就有点CPU 的分时使用的概念.
pgbouncer连接池模式:
pgbouncer支持三种连接池模式:
- session 这里是针对session来说的,当用户主动释放了连接,pgbouncer才会把其与数据库之间管理的连接进行释放复用。这样的设置本身和PG的连接逻辑的意义基本上一致.所以还不如不用,一般不使用这种模式。
- Transaction 最常用也是最合适的模式,一个连接的通道分时被 事务 所使用, 这样的好处比上面的session模式对比要明显的多,连接的使用率会跟随相关的分配有更高的复用,和性能方面的提高.当事务从客户端发出之后,pgbouncer会在与数据库之间的连接中找到一个连接是idle的去扔进去执行,完成事务之后,连接将重新被pgbouncer 交给给其他新事务去使用。
- SQL 类似于autocommit,粒度最细,一条SQL执行即释放连接,连接就会被其他会话所占用掉。虽然资源利用最极致,但是不符合一般业务场景。破坏了事务逻辑。
我们在使用pgbouncer的情况下,应该首选的是transaction 而不是session否则基本上大部分环节下(于业务以及相关设计以有关),session并不能帮助你做什么特别大的改变,大部分连接处于等待的状态.
pgbouncer特点:
a.内存消耗低(默认为2k/连接),因为Bouncer不需要每次都接受完整的数据包
b.可以把不同的数据库连接到一个机器上,而对客户端保持透明
c.支持在线的重新配置而无须重启
d.仅支持V3协议,因此后端版本须>=7.4 (引自 pgsqldb中文站)
pgbouncer部署方式:
Pgbouncer没有绑定到一台后端服务器。目标数据库可以驻留在不同的主机上
单应用:单应用场景主要具体为短连接较多的场景,频繁进行数据库的连接操作,但操作时间较短,均为短连接,所以将pgbouncer于应用服务器部署在同一台服务器,减少应用服务器和pgbouncer之间的开销
多应用:多应用场景,一般指多个应用服务器连接数据库,因此可以选择将pgbouncer与数据库服务部署在同一台服务器上,减少pgbouncer和数据库之间的开销。
集群:读写分离场景下pgbouncer的配置与前面配置基本一致,主要区别于要针对读和写进行分别部署pgbouncer,因为pgbouncer本身只是数据库连接池,不具备负载均衡,或高可用,IP漂移等特性,需要结合其他成熟产品进行组合使用====多实例场景主要利用linux系统端口重用技术,这个特性依靠Linux内核上的支持(Linux3.6以上版本),并结合pgbouncer自身支持(设置so_reuseport=1)结合起来形成多实例场景下的pgbouncer使用,可以认为是pgbouncer的高可靠或者高可用,在某一个实例进程故障的情况下,其他实例集成仍然可以处理来自外部的数据库连接请求。从操作系统层面来看,属于多进程共享同一个端口
2.pgbouncer安装
2.1 linux安装
核心的是pgbouncer.ini配置:
[databases]
kkdb= host=192.168.120.149 port=5432 user=kkuser password=redhat dbname=a //dbname为实际数据库名,kkdb为a在pgbouncer中的名字,所以在pgbouncer链接的数据库kkdb,实际上是连的a。
postgres= host=192.168.120.149 port=5432 user=postgres password=redhat dbname=b
[pgbouncer]
logfile = /var/log/pgbouncer/pgbouncer.log
pidfile = /var/run/pgbouncer/pgbouncer.pid
listen_addr = * //127.0.0.1表示local访问,*表示可以外部访问
listen_port = 6432
auth_type = md5
auth_file = /etc/pgbouncer/userlist.txt
admin_users = postgres,kkuser
pool_mode = transaction //用trancation才能体现pgbouncer的优势。
server_reset_query = DISCARD ALL
ignore_startup_parameters = extra_float_digits
max_client_conn = 1000
default_pool_size = 200
启动pgbouncer ,这里必须以postgresql服务器用户启动,例如postgres。这里需要把pgbouncer的安装目录修改权限为postgres账户
按此配置,启动pgbouncer后,可以psql -h pgbouncer的ip -p 6432 -U postgres pgbouncer登录pgbouncer,可以把pgbouncer看做一个虚拟的数据库,登录用户为admin_users里面的用户,默认postgres用户。
可以psql -h pgbouncer的ip -p 6432 -U postgres postgres 登录到数据库b
可以psql -h pgbouncer的ip -p 6432 -U kkuser kkdb 登录到数据库a
2.2 docker安装
rancher拉取相应镜像,并配置Environment Variables,然后配置好sevices和ingress,就可以通过2.1中的psql访问了。可详细访问https://hub.docker.com/r/bitnami/pgbouncer中关于镜像和Variables介绍。
3.pgbouncer命令及配置详解
看了很多关于pgbouncer命令配置的帖子,觉得讲的比较细的,可参考https://www.bigtspace.com/archives/9903.html
命令是指登录pgbouncer后可使用的命令,配置是指pgbouncer.ini中各项配置。
4.pgbouncer项目中使用
springboot中使用,主要是修改url为pgbouncer对应的ip和port,数据库名为pgbouncer.ini中database部分数据库配置最靠前的内容,,,这种url也可以通过数据库链接工具,来通过pgbouncer链接到实际数据库,前提是pgbouncer.ini中的listen_addr = * ,*表示可以外部访问
spring:
datasource:
url: jdbc:postgresql://192.168.120.149(pgbouncer ip):6432(pgbouncer port)/kkdb(pgbouncer.ini中database部分数据库配置最靠前的内容)?prepareThreshold=0
driverClassName: org.postgresql.Driver
username: kkuser(pgbouncer中database中数据库对应的用户名)
password: redhat (pgbouncer中database中数据库对应的密码)
5.pgbouncer效果
由于云服务器中病毒,暂时不能展示,后期有时间补上。
欢迎批评指正!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· 上周热点回顾(3.3-3.9)
· winform 绘制太阳,地球,月球 运作规律