【发布时间】:2015-07-06 21:23:31
【问题描述】:
假设一个 Java 应用程序正在打开 JDBC 连接到 Postgres,AutoCommit 设置为 false。
在这样的 JDBC 连接上,如果我们执行 SQL SELECT 命令,那么事务边界会发生什么?即使 AutoCommit 已关闭,是否存在任何隐含事务边界?
【问题讨论】:
标签: java postgresql jdbc
假设一个 Java 应用程序正在打开 JDBC 连接到 Postgres,AutoCommit 设置为 false。
在这样的 JDBC 连接上,如果我们执行 SQL SELECT 命令,那么事务边界会发生什么?即使 AutoCommit 已关闭,是否存在任何隐含事务边界?
【问题讨论】:
标签: java postgresql jdbc
6ton 是对的,这个答案应该被接受。我只是想详细说明一下。
您的应用程序将留下空闲的未处理事务。这可以防止一些清理工作,因为 PostgreSQL 无法将事务标记为最终提交或回滚。不做任何写操作也没关系(因为没有分配事务ID),但仍应避免。
如果您选择一个有副作用的函数,这些副作用将不会被提交,并且会在您断开连接时丢失。
如果您由于配置、数据库设置或用户默认设置而使用SERIALIZABLE 隔离,您将看到在第一个SELECT 拍摄的快照中的数据。由于无法VACUUM 删除旧行而导致的膨胀,您还会遇到数据库性能问题。这不会发生在 READ COMMITTED 隔离中。
您确实应该正确地执行此操作,并且自动提交或使用显式事务划分。
【讨论】:
自动提交不会有任何效果,因为您只是触发选择。
默认事务隔离级别将对 select 子句起作用 - 对于 postgres,它设置为 READ_COMMITTED。来自docs:
Read Committed 是 PostgreSQL 中的默认隔离级别。当一个 事务使用这个隔离级别,一个 SELECT 查询(没有 FOR UPDATE/SHARE 子句)只看到查询开始前提交的数据; 它永远不会看到未提交的数据或期间提交的更改 通过并发事务执行查询。
【讨论】: