无 Spring 环境下 Java 事务控制核心是 JDBC Connection 三步:关闭 autoCommit、执行操作、显式 commit/rollback;必须在获取连接后立即设 autoCommit=false,异常时必须 rollback 并妥善处理 rollback 异常,资源须用 try-with-resources 或 finally 严格释放,可选 Savepoint 实现部分回滚。

在无 Spring 环境下,Java 事务控制完全依赖 JDBC 的 Connection 接口,核心就是三步:关自动提交 → 执行操作 → 显式 commit 或 rollback。关键不在“能不能做”,而在于“怎么做得健壮、可复用、不漏资源”。下面直接讲清楚实操要点。
必须关闭 autoCommit 才算开启事务
JDBC 默认每条 SQL 都自动提交,本质是无数个单语句小事务。要让多条 SQL 绑定在一个事务里,唯一前提是调用 connection.setAutoCommit(false)。这行代码等价于 SQL 中的 START TRANSACTION,不是可选项,是起点。
- 必须在获取 Connection 后、执行任何 SQL 前设置,否则已执行的语句已提交,无法回滚
- 设为 false 后,后续所有 Statement/PreparedStatement 操作都归属该事务上下文
- 即使只执行一条 UPDATE,只要关了 autoCommit,它就处于未提交状态,直到显式 commit 或 rollback
异常路径必须保证 rollback,且不能吞异常
事务失败时 rollback 不是“最好做”,而是“必须做”,否则连接会卡在未提交状态,可能锁表或耗尽连接池资源。
- rollback 要放在 catch 块中,并捕获 SQLException;其他运行时异常(如 NullPointerException)也应触发 rollback
- rollback 本身可能抛 SQLException(比如网络断开),需单独 try-catch,但不能因此跳过 rollback 尝试
- 不要用空 catch 吞掉 rollback 异常,至少 log.warn("rollback failed, connection may be in inconsistent state")
资源释放要严格遵循 finally 或 try-with-resources
Connection、Statement、ResultSet 都是重量级资源,必须显式 close,否则极易引发连接泄漏。
立即学习“Java免费学习笔记(深入)”;
- 推荐用 try-with-resources:Connection 和 PreparedStatement 都实现了 AutoCloseable,能自动释放
- 若手动 close,务必在 finally 块中,且每个 close 都单独 try-catch(避免前一个 close 抛异常导致后续资源未释放)
- 注意:rollback/commit 后仍需 close 连接,它们不等于关闭连接
可选但强烈建议:使用 Savepoint 实现部分回滚
当一个事务内有多个逻辑段,希望某一段失败时不连累前面已完成的操作,可用 Savepoint。
- 调用
connection.setSavepoint()创建保存点,返回 Savepoint 对象 - 出错时调用
connection.rollback(savepoint)回滚到该点,而非整个事务 - 注意:Savepoint 依赖数据库驱动支持(MySQL 5.6+、PostgreSQL 支持良好;Oracle 全面支持;H2 支持)
- 示例场景:批量导入数据,前 9 条成功、第 10 条违反唯一约束 → rollback 到第 9 条后的 savepoint,继续处理后续


















