package scripts.qa; import java.io.File; import java.nio.file.Files; import java.sql.*; /** * 真实 Kingbase 数据库 ROLLBACK-ONLY 事务回滚验证脚本。 * 严禁 COMMIT 任何测试数据。验证真实数据库事务原子性与回滚机制。 */ public class ValidateRealDbRollback { public static void main(String[] args) throws Exception { Class.forName("com.kingbase8.Driver"); File envFile = new File(System.getProperty("user.home"), ".railwaysystem-qa.env"); String pass = ""; if (envFile.exists()) { for (String line : Files.readAllLines(envFile.toPath())) { line = line.trim(); if (line.startsWith("QA_DB_PASSWORD=")) { pass = line.substring("QA_DB_PASSWORD=".length()).trim(); if (pass.startsWith("\"") && pass.endsWith("\"")) { pass = pass.substring(1, pass.length() - 1); } } } } if (pass.isEmpty()) { throw new IllegalStateException("QA_DB_PASSWORD is required in ~/.railwaysystem-qa.env"); } // 尝试直连或通过 SSH 端口转发 (14321) 连接 String dbUrl = "jdbc:kingbase8://127.0.0.1:14321/railwaysystem_integrated_qa_20260916?useUnicode=true&characterEncoding=utf8"; try (Connection conn = DriverManager.getConnection(dbUrl, "kingbase", pass)) { System.out.println("CONNECTED_TO_DB=TRUE"); // 1. 验证当前数据库身份 try (Statement st = conn.createStatement(); ResultSet rs = st.executeQuery("SELECT current_database(), current_user")) { if (rs.next()) { System.out.println("CURRENT_DATABASE=" + rs.getString(1)); System.out.println("CURRENT_USER=" + rs.getString(2)); if (!"railwaysystem_integrated_qa_20260916".equals(rs.getString(1))) { throw new IllegalStateException("数据库身份不符,安全终止!"); } } } // 2. 选择一条安全的已有记录读取原始状态 String targetPlanId = null; int originalPlanStatus = -1; long targetEnrollmentId = -1; int originalEnrollmentStatus = -1; String selectSampleSql = "SELECT p.plan_id, p.plan_status, e.enrollment_id, e.enrollment_status " + "FROM train_class_plan p " + "JOIN train_enrollment e ON e.plan_id = p.plan_id " + "LIMIT 1"; try (Statement st = conn.createStatement(); ResultSet rs = st.executeQuery(selectSampleSql)) { if (rs.next()) { targetPlanId = rs.getString(1); originalPlanStatus = rs.getInt(2); targetEnrollmentId = rs.getLong(3); originalEnrollmentStatus = rs.getInt(4); } } if (targetPlanId == null) { System.out.println("NO_SAMPLE_DATA_FOUND"); return; } System.out.println(String.format("SAMPLE_BEFORE: plan_id=%s, plan_status=%d, enrollment_id=%d, enrollment_status=%d", targetPlanId, originalPlanStatus, targetEnrollmentId, originalEnrollmentStatus)); // 3. 开启事务 (禁用 AutoCommit) conn.setAutoCommit(false); try { // 在未提交事务中模拟结训更新 int mockPlanTargetStatus = (originalPlanStatus == 2) ? 1 : 2; int mockEnrollmentTargetStatus = (originalEnrollmentStatus == 4) ? 1 : 4; try (PreparedStatement pst = conn.prepareStatement( "UPDATE train_class_plan SET plan_status = ?, update_time = now() WHERE plan_id = ?")) { pst.setInt(1, mockPlanTargetStatus); pst.setString(2, targetPlanId); pst.executeUpdate(); } try (PreparedStatement pst = conn.prepareStatement( "UPDATE train_enrollment SET enrollment_status = ?, complete_time = now() WHERE enrollment_id = ?")) { pst.setInt(1, mockEnrollmentTargetStatus); pst.setLong(2, targetEnrollmentId); pst.executeUpdate(); } // 事务内查看临时修改值 int inTxPlanStatus = -1; int inTxEnrollStatus = -1; try (Statement st = conn.createStatement(); ResultSet rs = st.executeQuery("SELECT p.plan_status, e.enrollment_status FROM train_class_plan p JOIN train_enrollment e ON e.plan_id = p.plan_id WHERE p.plan_id = '" + targetPlanId + "' AND e.enrollment_id = " + targetEnrollmentId)) { if (rs.next()) { inTxPlanStatus = rs.getInt(1); inTxEnrollStatus = rs.getInt(2); } } System.out.println(String.format("IN_TRANSACTION_MODIFIED: plan_status=%d, enrollment_status=%d", inTxPlanStatus, inTxEnrollStatus)); // 4. 显式执行主动 ROLLBACK (严禁 COMMIT) conn.rollback(); System.out.println("TRANSACTION_ROLLED_BACK=TRUE"); } catch (Exception ex) { conn.rollback(); throw ex; } finally { conn.setAutoCommit(true); } // 5. 验证回滚后数据完全恢复原样 int afterRollbackPlanStatus = -1; int afterRollbackEnrollStatus = -1; try (Statement st = conn.createStatement(); ResultSet rs = st.executeQuery("SELECT p.plan_status, e.enrollment_status FROM train_class_plan p JOIN train_enrollment e ON e.plan_id = p.plan_id WHERE p.plan_id = '" + targetPlanId + "' AND e.enrollment_id = " + targetEnrollmentId)) { if (rs.next()) { afterRollbackPlanStatus = rs.getInt(1); afterRollbackEnrollStatus = rs.getInt(2); } } System.out.println(String.format("AFTER_ROLLBACK_VERIFIED: plan_status=%d, enrollment_status=%d", afterRollbackPlanStatus, afterRollbackEnrollStatus)); boolean intact = (originalPlanStatus == afterRollbackPlanStatus) && (originalEnrollmentStatus == afterRollbackEnrollStatus); if (intact) { System.out.println("REAL_DB_TRANSACTION_ROLLBACK_VALIDATION=PASS"); } else { System.err.println("REAL_DB_TRANSACTION_ROLLBACK_VALIDATION=FAIL (Data altered!)"); System.exit(1); } } } }