PostgreSQL 16如何并发刷新SQL物化视图

陌萱姑娘_3474

陌萱姑娘_3474

2026-08-22

621人浏览

原创

PostgreSQL 16中加CONCURRENTLY仍报“does not have a unique index”是因为命令入口即校验硬性前提:必须显式在物化视图上创建覆盖全部分组列、全NOT NULL、无函数表达式的VALID唯一索引,缺一则直接拒绝执行,不进入刷新阶段。

postgresql 16如何并发刷新sql物化视图

PostgreSQL 16 不支持真正的增量刷新,REFRESH MATERIALIZED VIEW CONCURRENTLY 仍是全量执行 + 差集比对,但能避免读锁;它能跑起来的唯一前提是:物化视图上必须有满足全部硬性条件的唯一索引。

为什么加了 CONCURRENTLY 还报 “does not have a unique index”

这不是配置漏了、权限不够,而是 PostgreSQL 16 在命令入口就做校验:没索引,直接拒掉,根本不会进执行阶段。错误信息固定为:ERROR: cannot refresh materialized view "xxx" concurrently, because it does not have a unique index。

  • 索引必须显式建在物化视图上,CREATE UNIQUE INDEX ON my_mv (id) —— 源表有主键、或约束带唯一性,都不算数
  • 所有索引列必须 NOT NULL;如果字段允许 NULL,得用 COALESCE(col, 0) 或类似兜底后再建索引
  • 聚合类视图(如含 GROUP BY tenant_id, event_type)必须把全部分组列放进索引,顺序也要一致,(tenant_id, event_type) 不能写成 (event_type, tenant_id)
  • 刚建完索引可能状态是 INVALID,需执行一次 VACUUM my_mv 或 ANALYZE my_mv 才被识别
  • 表达式索引(如 (UPPER(name)))、带 WHERE 条件的索引、函数索引,一律不被接受

CONCURRENTLY 刷新失败的常见真实原因

即使索引建对了,刷新仍可能中途失败,且失败后物化视图处于“部分更新”状态 —— 旧数据没全删、新数据没全写,不可靠。

  • 业务写入与新数据产生唯一键冲突:ERROR: duplicate key value violates unique constraint(比如新数据要插 order_id = 123,但业务刚好 INSERT 了同 ID 的行)
  • 某行在 merge 阶段前被业务 UPDATE 过:could not lock updated tuple in materialized view
  • 物化视图刚创建、还没填充过(即处于 WITH NO DATA 状态),CONCURRENTLY 会直接拒绝 —— 必须先用普通 REFRESH MATERIALIZED VIEW my_mv 填一次
  • 定义中含不可重放表达式:now()、random()、CURRENT_USER,或未配 ORDER BY 的 DISTINCT ON / 窗口函数,导致新旧结果无法精确比对

性能和资源上容易被低估的开销

并发刷新不是“更快”,而是“可读”,实际代价往往更高。

Summarizer
Summarizer

一款基于AI的在线文本摘要工具,可将较长的文章和文字内容提炼为更加简洁的核心信息,方便快速阅读和理解。

下载
  • 每次都要全量扫描源表 + 全量执行原始查询 + 两次索引扫描(新旧数据各一次)+ 差集计算,实测 400 万行下比普通刷新慢 3–4 倍
  • 临时副本需额外磁盘空间,高频刷新(如每分钟一次)极易触发 no space left on device
  • 它不阻塞 SELECT,但会阻塞某些 DML:比如对正在刷新的 MV 执行 UPDATE 或 DELETE 可能被锁住
  • 真正省时间的地方不在刷新命令本身,而在物化视图定义:去掉 DISTINCT ON、避免无序 json_agg、让聚合字段类型和 WHERE 条件严格一致(比如别用 EXTRACT(YEAR FROM ts) = 2023,该写 EXTRACT(YEAR FROM ts)::int = 2023)

想“增量”,只能自己控范围

PostgreSQL 内核不提供基于 WAL 或变更日志的增量能力。CONCURRENTLY 不是增量,只是“全量查 + 全量比 + 差异写”。真要减少数据量,得靠外部逻辑:

  • 手动维护位点:建一张 matview_refresh_state 表存上次最大 updated_at,刷新 SQL 中加 WHERE updated_at > ?
  • 用 pg_matview 扩展:本质是把 MV 当普通表 + 触发器捕获变更 + 手写 INSERT ON CONFLICT,它不自动推导变化行,只帮你搭个壳
  • 前提是你有可靠单调递增字段(如自增 ID、严格递增时间戳),否则边界判定会出错

最常被忽略的一点:索引结构必须在建物化视图时就设计好,而不是等 CONCURRENTLY 报错才回头改。一旦 MV 数据量上去,重建索引或改结构的成本远高于初期多花十分钟选对主键语义。

相关文章

PHP速学视频免费教程(入门到精通)
PHP速学视频免费教程(入门到精通)

PHP怎么学习?PHP怎么入门?PHP在哪学?PHP怎么学才快?不用担心,这里为大家提供了PHP速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载

相关标签:

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

相关专题

更多
postgresql常用命令
postgresql常用命令

postgresql常用命令psql、createdb、dropdb、createuser、dropuser、\l、\c、\dt、\d table_name、\du、\i file_name、\e和\q等。本专题为大家提供postgresql相关的文章、下载、课程内容,供大家免费下载体验。

2023.10.10

233

5

常用的数据库软件
常用的数据库软件

常用的数据库软件有MySQL、Oracle、SQL Server、PostgreSQL、MongoDB、Redis、Cassandra、Hadoop、Spark和Amazon DynamoDB。更多关于数据库软件的内容详情请看本专题下面的文章。php中文网欢迎大家前来学习。

2023.11.02

4989

19

postgresql常用命令有哪些
postgresql常用命令有哪些

postgresql常用命令psql、createdb、dropdb、createuser、dropuser、\l、\c、\dt、\d table_name、\du、\i file_name、\e和\q等。更详细的postgresql常用命令,大家可以访问下面的文章。

2023.11.16

647

3

postgresql常用命令介绍
postgresql常用命令介绍

postgresql常用命令有\l、\d、\d5、\di、\ds、\dv、\df、\dn、\db、\dg、\dp、\c、\pset、show search_path、ALTER TABLE、INSERT INTO、UPDATE、DELETE FROM、SELECT等。想了解更多postgresql的相关内容,可以阅读本专题下面的文章。

2023.11.20

1396

6

PostgreSQL性能优化与索引调优实战
PostgreSQL性能优化与索引调优实战

本专题面向后端开发与数据库工程师,深入讲解 PostgreSQL 查询优化原理与索引机制。内容包括执行计划分析、常见索引类型对比、慢查询优化策略、事务隔离级别以及高并发场景下的性能调优技巧。通过实战案例解析,帮助开发者提升数据库响应速度与系统稳定性。

2026.02.12

500

19

PostgreSQL 性能优化与查询执行计划实战
PostgreSQL 性能优化与查询执行计划实战

本专题深入解析PostgreSQL性能优化核心,聚焦查询执行计划的实战应用。通过EXPLAIN命令精准定位瓶颈,结合索引策略、SQL改写与参数调优,系统提升查询效率。从执行计划解读到性能调优全流程,助你掌握数据库性能诊断与优化实战能力。

2026.05.08

170

10

PostgreSQL 在 Next.js / Go 全栈架构中的工程化实践
PostgreSQL 在 Next.js / Go 全栈架构中的工程化实践

本文详解如何利用Next.js(搭配Drizzle ORM)与Go后端构建高性能应用,充分发挥PG在JSONB非结构化存储与pgvector向量检索上的优势。从数据建模到Docker容器化部署,打造支持AI时代的“One Database”工程化解决方案。

2026.05.08

921

10

PostgreSQL高级特性、内核机制与现代数据架构
PostgreSQL高级特性、内核机制与现代数据架构

本专题从MVCC并发控制与WAL日志等内核机制出发,详解JSONB、PostGIS及pgvector等高级特性。探讨如何利用单一引擎支撑关系型、向量及图数据等现代数据架构需求,助您掌握构建高并发、智能化应用的核心技术。

2026.05.08

264

10

数据库三范式
数据库三范式

数据库三范式是一种设计规范,用于规范化关系型数据库中的数据结构,它通过消除冗余数据、提高数据库性能和数据一致性,提供了一种有效的数据库设计方法。本专题提供数据库三范式相关的文章、下载和课程。

2023.06.29

3225

3

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
热门推荐
/
最新课程
phpStudy极速入门视频教程
phpStudy极速入门视频教程

共6课时 | 54.7万人学习

独孤九贱(4)_PHP视频教程
独孤九贱(4)_PHP视频教程

共89课时 | 134.3万人学习