PostgreSQL v18发布,新增AIO uuidv7 OAuth等功能

大家好,我是农村程序员,独立开发者,行业观察员,前端之虎陈随易。

如果本文能给你提供启发或帮助,欢迎动动小手指,一键三连(点赞评论转发),给我一些支持和鼓励,谢谢。


PostgreSQL 18.0 更新速览:AIO、uuidv7、OAuth、pg_stat_io(以及升级要注意的坑)

PostgreSQL 18.0(Release date: 2025-09-25)这版,我看完 release notes 之后的感受是:

这不是"修修补补",这是"从内核到体验"的一轮升级。

官方 release notes 在这里(建议收藏):

(说明:本文以 PostgreSQL 18.0 release notes + v18 文档为准;18.x 小版本一般以 bugfix 为主,不影响本文对"大特性"的理解。)

下面我挑一些我觉得 重要 / 有趣 / 真能用起来 的点,尽量用人话讲清楚。


1)AIO:数据库终于开始"认真并发读写"

PostgreSQL 18 引入了 异步 I/O(AIO)子系统,会影响(并且可能加速)这些典型场景:

  • 顺序扫描(sequential scans)
  • bitmap heap scans
  • VACUUM / ANALYZE
  • 以及一堆"会读很多数据"的操作

官方描述里一个很关键的点是:后端可以一次性排队多个 read 请求,让顺序扫描、vacuum 等更高效。

怎么开?

核心开关是 io_method(需要重启生效):

  • worker:用 I/O worker 进程执行异步 I/O(默认)
  • io_uring:用 Linux io_uring(需要编译时启用 liburing)
  • sync:把"可异步的 I/O"同步执行(等于先别折腾)

配套还有:

  • io_workers:worker 模式下 I/O worker 数量
  • io_combine_limit / io_max_combine_limit:控制合并 I/O 的最大 size

另外,release notes 里还提到:AIO 的引入,也让一些系统在没有 fadvise() 支持时,effective_io_concurrency / maintenance_io_concurrency 也能设置为 > 0。

怎么观测?

PG18 新增系统视图 pg_aios,能看到正在使用的 AIO handle(偏开发/调优向,但很好用):

以及等待事件里也能看到 AIO 相关项(比如 io_uring submit/execution)。

如果你是 DBA/运维同学,我的建议是:

  1. 先在压测环境开 io_method=worker 看收益
  2. 结合 pg_stat_io(后面会讲)观察读写 bytes、fsync 等指标
  3. 再考虑是否值得为 io_uring 做编译与内核/文件系统/权限层面的投入

2)pg_upgrade 不再"升级后冷启动":开始保留优化器统计信息

以前大版本升级常见一个尴尬期:

你升级成功了,但统计信息没了,执行计划像"刚装系统一样",性能波动一阵子。

PostgreSQL 18 的 pg_upgrade 默认会转移大部分 optimizer statistics (可以用 --no-statistics 关闭)。

官方文档也说得很清楚:

  • 并不是所有统计都能转(比如 CREATE STATISTICS 这类 extended statistics 不一定保留)
  • 升级后依然建议补一轮统计生成

pg_upgrade 文档对应章节:

它甚至给出了建议流程:先用 缺失统计补齐模式 快速补缺,再全量 analyze 保证齐全。

这里我把命令写得更精确一点(避免误用):

  • 先跑:vacuumdb --all --analyze-in-stages --missing-stats-only

    • 注意:--missing-stats-only 只能--analyze-only / --analyze-in-stages 搭配使用(它的目的就是"只补缺失的统计信息")。
  • 再跑:vacuumdb --all --analyze-only

我个人非常喜欢这一点:属于"升级体验"级别的优化


3)Skip Scan:多列 B-tree 索引终于没那么"左前缀死板"了

PostgreSQL 18 加了 B-tree skip scan。这句话的实际含义是:

多列 B-tree 索引,在"缺少前导列等值条件"的情况下,也有机会被用上。

多列索引的经典规则是:对最左列(leading column)约束越强越有用;如果你只约束了后面的列,往往扫很大一段索引甚至干脆不用。

skip scan 的做法是:在某些情况下,PG 会在内部生成"动态等值约束",通过多次 index search 来"跳过"不可能命中的索引叶子页,从而减少要读的索引范围。

官方在"多列索引"章节里直接解释了 skip scan,并给了例子:

  • 索引 (x, y),查询 WHERE y = 7700,有可能用 skip scan
  • 但通常只有在 x 的 distinct 值很少、能跳过大量 leaf page 时才划算

文档在这里(强烈推荐读一遍):

我对这个特性的评价:

  • 对写业务的同学:不用你改 SQL,就可能变快(当然要看数据分布)
  • 对做索引设计的同学:以前"不敢建"的多列索引,现在可能更值钱

4)uuidv7():时间有序 UUID,写入与索引更友好

PG18 内置了 uuidv7():生成 timestamp-ordered 的 UUID(版本 7)。

官方函数文档里写得很明确:

  • uuidv7() 使用 UNIX timestamp(毫秒精度)+ 次毫秒时间 + random
  • 可选参数 shift interval 可以让生成时间偏移

对应文档:

顺带还有两个很实用的"解剖函数":

  • uuid_extract_timestamp(uuid):从 v1/v7 UUID 里提取时间戳
  • uuid_extract_version(uuid):提取版本号

为什么我说它"真能用起来"?因为很多系统以前用 UUIDv4(完全随机),在 B-tree 上写入会更像"到处插",页分裂/缓存局部性都比较尴尬。

uuidv7 这种"时间大致有序"的特性,在一些高写入场景(尤其主键就是 UUID 的表)会更舒服。


5)Generated Columns:默认变成 VIRTUAL(省空间,但也有坑)

PostgreSQL 18 增强了 generated columns:

  • 支持 VIRTUAL generated columns(读取时计算,不占存储)
  • 并且 VIRTUAL 现在是默认(在 PostgreSQL 18 之前,generated column 只有 STORED)

语法仍然是:

GENERATED ALWAYS AS (expr) [ STORED | VIRTUAL ]

官方文档在 CREATE TABLE 参数里写得很细:

  • VIRTUAL:读取时算,不占磁盘
  • STORED:写入时算,落盘
  • 生成表达式必须 immutable

并且还有一个非常重要的限制(很多人会踩):

虚拟 generated column 不能使用用户自定义类型,且表达式不能引用用户自定义函数/类型(只能用内置函数/类型)。

文档:

我的建议是:

  • 你要的是"存储空间/写入开销更低",或者表达式经常改:选 VIRTUAL(默认就是)
  • 你要的是"读性能稳定"、表达式复杂且允许用自定义函数:用 STORED

6)RETURNING 终于支持 old/new:审计、diff、业务回写都舒服了

PG18 给 DML 的 RETURNING 加了 old / new

  • INSERT / UPDATE / DELETE / MERGE 都能显式取 old/new
  • 典型用法是:一次 SQL 就把"变更前后"带回来,不用再查一遍

官方文档例子(我直接抄核心模式):

sql 复制代码
UPDATE products
SET price = price * 1.10
WHERE price <= 99.99
RETURNING
	name,
	old.price AS old_price,
	new.price AS new_price,
	new.price - old.price AS price_change;

文档:

另外一个小细节:

  • INSERT 通常 old 为 NULL
  • DELETE 通常 new 为 NULL

但在 INSERT ... ON CONFLICT DO UPDATE 这种场景,old/new 都可能有意义。


7)OAuth:PostgreSQL 也开始对接企业"票据体系"

PostgreSQL 18 新增 OAuth 认证方式:

  • pg_hba.conf 里会出现 oauth 认证方法
  • libpq(psql/应用)侧有对应 OAuth 选项
  • 需要编译时启用 libcurl(release notes 里明确提到 --with-libcurl

OAuth 文档里有几个点值得高亮:

  1. 服务器端要配置 issuerscope
  2. issuer 与 discovery document 的 issuer identifier 必须严格匹配(大小写/格式都不允许差一点点)
  3. validator/oauth_validator_libraries 负责 token 校验(不同部署会很不一样)

文档:

我对 OAuth 的理解:

  • 对企业内网、数据平台、统一登录场景,这是"终于等到官方支持"的那种特性
  • 但这块落地成本也不低,尤其是 validator 的实现与安全边界要设计清楚

8)可观测性:pg_stat_io 更细、还能看每个 backend 的 I/O/WAL

这一块是我觉得 PG18 最"运营友好"的升级之一。

8.1 pg_stat_io 终于开始按 bytes 统计

release notes 明确提到:

  • pg_stat_io 增加了 read_bytes / write_bytes / extend_bytes
  • 以前那个永远等于 BLCKSZop_bytes 被移除了
  • 还增加了 WAL I/O 行(包括 wal receiver 等)

对应文档里对 pg_stat_io 的定义也很清晰(backend_type / object / context 三维组合):

你可以先从这种查询开始:

sql 复制代码
SELECT backend_type, object, context,
			 reads, read_bytes,
			 writes, write_bytes,
			 fsyncs, fsync_time
FROM pg_stat_io
ORDER BY read_bytes DESC NULLS LAST;

8.2 每个 backend 的 I/O 统计:定位"谁在折腾磁盘"

PG18 增加了:

  • pg_stat_get_backend_io(pid):拿到某个 pid 的 I/O 统计(字段同 pg_stat_io)

文档:

这对排查"到底是谁在大量 bulkread/bulkwrite/vacuum I/O"很有帮助。


9)升级前必看的兼容性变化(别踩坑)

PG18 有一些变化,我建议升级前就拉一张 checklist(这里挑几个最容易影响到人的):

9.1 initdb 默认开启 data checksums

PG18 改成:initdb 默认启用数据校验和(data checksums)。

  • 可以用 initdb --no-data-checksums 关掉
  • pg_upgrade 要求新旧集群 checksum 设置一致,所以这个选项对升级"旧集群没开 checksum"的场景很关键

(这一条在 release notes 的 incompatibilities 里写得很明确。)

9.2 MD5 password 认证被标记为弃用

MD5 password authentication 进入弃用状态:

  • 未来大版本会移除
  • CREATE ROLE/ALTER ROLE 设置 MD5 password 会发 deprecation warning
  • 可通过 md5_password_warnings=off 关闭警告(但不建议掩耳盗铃,还是尽快迁移到更安全的方式,比如 SCRAM)

9.3 VACUUM / ANALYZE 默认会处理继承子表

PG18 改了行为:对父表执行 VACUUM/ANALYZE 时,会处理 inheritance children(对分区表也类似:默认会处理子分区)。

  • 以前那种"只处理父表"的行为,现在要用 ONLY 选项显式表达

9.4 COPY FROM CSV 不再把 \. 当 EOF

PG18 不再在 CSV 模式下把 \. 当作 EOF 标记。

  • psql 仍然会在从 STDIN 读 CSV 时把 \. 当 EOF
  • 旧版本 psql 连到 PG18 服务器,使用 \copy 可能会出问题
  • 并且这版还要求 \. 必须独占一行

这类变化看似边角,但线上一旦命中就很致命。


我个人最喜欢的 3 个更新

如果你问我:PG18 这么多条,哪 3 个最值得立刻关注?我会选:

  1. AIO 子系统:它不只是"快一点",它改变的是 PG 面对现代存储/现代 I/O 的方式。
  2. pg_upgrade 保留统计信息:升级体验变得更稳定、更可控。
  3. pg_stat_io + per-backend I/O:排障与调优终于更"有数据支撑"。

参考链接

相关推荐
java1234_小锋2 小时前
[免费]基于Python的Flask+Vue物业管理系统【论文+源码+SQL脚本】
后端·python·flask·物业管理
一只小阿乐2 小时前
react 中的组件性能优化
前端·javascript·react.js·react组件性能优化
柯南二号2 小时前
【大前端】【iOS】iOS 真实项目可落地目录结构方案
前端·ios
肉清2 小时前
linux自用命令
linux·服务器·前端
weibkreuz2 小时前
初始React@1
前端·react.js·前端框架
konna2 小时前
3D模型AI生成技术分享
后端
Coder_Boy_2 小时前
前端和后端软件系统联调经典问题汇总
java·前端·驱动开发·微服务·状态模式
用户298698530142 小时前
如何在 C# .NET 中将 Markdown 转换为 PDF 和 Excel:完整指南
后端·c#·markdown
golang学习记2 小时前
Jetbrains 下一代 IDE Fleet:倒下了!
后端