PostgreSQL游标是否基于快照运行?是否存在非重复读?
PostgreSQL中游标的快照行为说明
核心规则
PostgreSQL的游标完全基于打开时刻的事务快照运行,不会读取到游标打开后其他事务提交的数据,也不会出现脏读(PostgreSQL默认不支持READ UNCOMMITTED隔离级别,实际会降级为READ COMMITTED,该级别下天然避免脏读)。
对应你的场景验证
按你给出的步骤:
- T1=00:00:01打开游标
- 读取第一批数据,对应T1时刻的表状态
- T2=00:00:05另一事务提交全量数据修改
- 读取第二批数据时,依然会获取T1时刻的表数据,看不到T2时刻的修改内容。
补充细节
- 游标属于当前事务的执行上下文,遵循PostgreSQL的MVCC(多版本并发控制)机制:打开游标时,系统会为当前事务生成一个数据快照,后续游标所有的分批读取操作都基于这个快照,直到游标关闭或事务结束。
- 如果需要获取游标打开后的数据变更,你需要关闭现有游标并重新打开(此时会生成新的事务快照);或者使用
DECLARE ... WITH HOLD创建持留游标——不过持留游标在事务提交后会切换到提交时刻的快照,这属于特殊使用场景。 - 无论游标是否标记为
INSENSITIVE(不敏感),只要是在同一个事务内打开的游标,都会基于打开时的快照读取数据,不会随表数据的后续变更而变化。
内容的提问来源于stack exchange,提问作者potato_programmer
相关产品推荐
相关产品推荐

