文档

Shared Server

更新时间:

本文介绍了PolarDB PostgreSQL版的Shared Server功能。

前提条件

支持的PolarDB PostgreSQL版版本如下:

PostgreSQL 11(内核小版本1.1.30及以上)

说明

您可通过如下语句查看PolarDB PostgreSQL版的内核小版本的版本号:

show polar_version;

背景信息

原生PostgreSQL的连接调度方式是每一个进程对应一个连接 (One-Process-Per-Connection),这种调度方式适合低并发、长连接的业务场景。而在高并发或大量短连接的业务场景中,进程的大量创建、销毁以及上下文切换,会严重影响性能。同时,在业务容器化部署后,每个容器通过连接池向数据库发起连接,业务在高峰期会弹性扩展出很多容器,后端数据库的连接数会瞬间增高,影响数据库稳定性,导致OOM频发。

为了解决上述问题,在使用PostgreSQL时通常会配置连接池组件。例如,部署在数据库侧的后置连接池PgBouncer,部署在应用侧的前置连接池Druid但后置连接池无法保留用户连接私有信息(例如,GUC参数、Prepared Statement)的相关功能,在面临进程被污染的情况(例如,加载动态链接库、修改role参数)时也无法及时清理。前置连接池不仅无法解决后置连接池的缺陷,还无法根据应用规模扩展而实时调整配置,仍然会面临连接数膨胀的问题。

PolarDB PostgreSQL版针对上述问题,从数据库内部提供了Shared Server(本文简称SS)内置连接池功能,采用共享内存+Session Context+Dispatcher转发+Backend Pool的架构,实现了用户连接与后端进程的解绑。后端进程具备了Native、Shared、Dedicated三种执行模式,并且在运行时可以根据实时负载和进程污染情况进行动态转换。负载调度算法充分吸收AliSQL对社区版MySQL线程池的缺陷改进,使用Stall机制弹性控制Worker数量,同时避免用户连接等待时间过长。从根本上解决了高并发或者大量短连接带来的性能、稳定性问题。

原理介绍

在PostgreSQL原生的One-Process-Per-Connection连接调度策略中,用户发起的连接与后端进程一一绑定:这里不仅是生命周期的绑定,同时还是服务与被服务关系的绑定。

原理介绍

在Shared Server内置连接池中,通过提取出会话相关上下文Session Context,将用户连接和后端进程进行了解绑,并且引入Dispatcher来进行代理转发:

image

  • Session Context保存Session相关数据,存放于共享内存中,跨进程共享。存放数据包括:Prepared Statement、连接私有参数、临时表元数据等,后续还可以不断扩展。

  • Dispatcher进程承载代理转发工作,用户连接通过Dispatcher分发调度到不同的后端进程上,后端进程通过Dispatcher被多个用户连接共享使用。Dispatcher进程可以配置多个。

  • 每个Dispatcher管理的后端进程按<user, database, GUCs>为key,划分成不同的后端进程池。每个后端进程池都有自己独占的后端进程组,单个后端进程池内的后端进程数量随着负载增高而增多,随着负载降低而减少。

  • 用户连接中的一个事务会始终被同一个后端进程服务,不同事务可能会被不同的后端进程服务。

image

在Shared Server中,后端进程有三种执行模式。进程执行模式在运行时会根据实时负载和进程污染情况进行动态转换:

  • Native模式(原生模式):一个后端进程只服务一个用户连接,不存在Dispatcher转发数据。

    • SS关闭后,所有后端进程都处于Native模式。

    • SS开启后,对于以下场景,后端进程也会在用户连接的登录阶段回退为Native模式:

      • WAL Sender进程。

      • MPP进程。

      • SS共享内存耗尽。

      • 在参数polar_ss_dedicated_dbuser_names黑名单范围内的数据库或用户。

  • Shared模式(共享模式):后端进程作为可共享的工作进程提供给各个用户连接使用。Shared模式是标准的、期望的连接池状态,表示后端进程是可复用的。SS开启后,后端进程会优先使用Shared模式,同时会在触发兜底机制时转换为Dedicated模式。

  • Dedicated模式(兜底模式):由于各种原因导致后端进程被污染,退化为当前后端进程只能服务当前用户连接,用户连接退出后,后端进程也退出。

    • 用户连接不再使用新的SS共享内存,而是使用本地进程内存。

    • 用户连接与后端进程之间的数据传输依旧经过Dispatcher转发。

    • 以下场景中会触发兜底机制,执行模式会由Shared转变为Dedicated:

      • 更新了SS黑名单内的GUC参数。

      • 使用了SS黑名单内的插件。

      • 执行了DECLARE CURSOR命令。

      • 对ONCOMMIT DELETE ROWS属性的表进行操作。

      • 执行CURSOR WITH HOLD操作。

      • 使用自定义GUC参数。

      • 加载动态链接库。

性能对比

Shared Server主要应用于高并发或大量短连接的业务场景,因此这里使用TPC-C进行测试。

TPC-C高并发

使用104核512 GB的物理机单机部署,测试TPC-C 1000仓下,并发数从300增大到5000时,不同配置下的分数对比。如下图所示:

  • old:不使用任何连接池,使用PostgreSQL的原生执行模式(即Native模式)。

  • ss off:使用Shared Server内置连接池,启动前关闭SS开关,退化为Native模式。

  • ss native:使用Shared Server内置连接池,启动后关闭SS开关,退化为Native模式。

  • ss didicated:使用Shared Server内置连接池,启动后开启SS开关,但强制使用Dedicated模式。

  • ss shared:使用Shared Server内置连接池,启动后开启SS开关,使用标准的Shared模式。

image

从图中可以看出:

  • 原生PostgreSQL场景、Shared Server关闭的场景、Shared Server兜底场景中,均无法稳定进行TPC-C高并发测试。性能从并发数为1500时开始下跌,在并发数为5000时已经不能提供服务。

  • Shared Server开启并进入Shared 模式后,TPC-C性能不受高并发数影响,始终保持在稳定状态,很好地支持了高并发场景。

PgBench短连接

使用104核512 GB的物理机单机部署,利用pgbench分别测试以下配置中,并发短连接数从1到128的场景下的性能表现:

  • pgbouncer session:使用PgBouncer后置连接池, 配置为Session Pooling模式。

  • pgbouncer transaction:使用PgBouncer后置连接池, 配置为Transaction Pooling模式。

  • old:不使用任何连接池,使用PostgreSQL的原生执行模式。

  • ss dedicated:使用Shared Server内置连接池,但强制设置为Dedicated模式。

  • ss shared:使用Shared Server内置连接池,配置为标准的Shared模式。

image

image从图中可以看出,使用连接池后,对于短连接,PgBouncer和Shared Server的性能均有所提升。但PgBouncer最高只能提升14倍性能,Shared Server最高可以提升42倍性能。

功能特性

PgBouncer对比

业界典型的后置连接池PgBouncer具有多种模式。其中Session Pooling模式仅对短连接友好,一般不使用;Transaction Pooling模式对短连接、长连接都友好,是默认推荐的模式。与PgBouncer相比,Shared Server的差异化功能特点如下所示:

功能

PgBouncer

Session Pooling

PgBouncer

Transaction Pooling

Shared Server

Startup parameters

受限

受限

支持

SSL

支持

支持

暂不支持

LISTEN/NOTIFY

支持

不支持

支持

触发兜底

LOAD statement

支持

不支持

支持

触发兜底

Session-level advisory locks

支持

不支持

支持

触发兜底

SET/RESET GUC

支持

不支持

支持

Protocol-level prepared plans

支持

暂不支持

支持

PREPARE / DEALLOCATE

支持

不支持

支持

Cached Plan Reset

支持

支持

支持

WITHOUT HOLD CURSOR

支持

支持

支持

WITH HOLD CURSOR

支持

不支持

暂不支持

PRESERVE/DELETE ROWS temp

支持

不支持

暂不支持

ON COMMIT DROP temp

支持

支持

支持

说明
  • PgBouncer的Startup参数仅包括:

    • client_encoding

    • datestyle

    • timezone

    • standard_conforming_strings

  • 触发进入Dedicated兜底模式,用户连接断开后,后端进程也会释放,避免污染后的进程被其他用户连接使用。

自定义配置

为了适应不同的环境,Shared Server支持丰富的参数配置:

  • 支持配置Dispatcher进程和后端进程的最大数量,可以实时调整出最佳性能模式。

  • 支持总连接数超过阈值后才启用SS的Shared模式,避免连接数较少时SS性能不显著。

  • 支持配置强制启用Dedicated模式,避免后端进程被污染后持续影响其他用户连接。

  • 支持配置指定的数据库/用户不使用Shared Server,给专用账户和管理员预留应急通道。

  • 支持配置指定插件不使用Shared Server,避免外部插件异常导致Shared Server不稳定。

  • 支持配置指定GUC参数不使用Shared Server,避免GUC功能复杂导致Shared Server不稳定。

  • 支持Dispatcher阻塞连接数量超过阈值后回退到Native模式,避免Dispatcher缺陷导致不可用。

  • 支持配置用户连接的超时等待时间,避免用户连接长时间等待后端进程。

  • 支持配置后端进程空闲时间阈值,避免后端进程长时间空闲,占用系统资源。

  • 支持配置后端进程活跃时间阈值, 避免后端进程长时间活跃,占用系统资源。

  • 支持配置每个后端进程池中保留后端进程的最小个数,保持连接池热度,避免进程被全部释放。

  • 支持配置Shared Server调试日志,方便排查后端进程调度相关的任何问题。

参数说明

Shared Server的典型配置参数说明如下:

参数

说明

polar_enable_shm_aset

是否开启全局共享内存。默认关闭,重启生效。取值如下:

  • on:开启全局共享内存。

  • off:关闭全局共享内存。

polar_ss_shared_memory_size

Shared Server全局共享内存的使用上限。单位为KB,取值为0时表示关闭,默认为1024 KB。重启生效。

polar_ss_dispatcher_count

Dispatcher进程的最大个数。默认为2,最大为CPU核数,建议配置与CPU核心数相同。重启生效。

polar_enable_shared_server

是否开启Shared Server功能,默认关闭。取值如下:

  • on:开启Shared Server功能。

  • off:关闭Shared Server功能。

polar_ss_backend_max_count

后端进程的最大数量,默认为-5,表示为max_connection的1/5;0-1表示与max_connection保持一致。建议设置为CPU核数的10倍。

polar_ss_backend_idle_timeout

后端进程的空闲退出时间,默认为3分钟。

polar_ss_session_wait_timeout

后端进程被用满时,用户连接等待被服务的最大时间,默认为60秒。

polar_ss_dedicated_dbuser_names

记录指定数据库/用户使用时进入Native模式。默认为空,取值如下:

  • d1/_:表示对使用数据库d1的任意连接,会回退到Native模式。

  • _/u1:表示使用用户u1的任意连接,会回退到Native模式。

  • d2/u2:表示使用数据库d2且用户u2的任意连接,会回退到Native模式。

  • 本页导读 (0)
文档反馈