Skip to content

Commit 4d19ea1

Browse files
committed
Fix for Bug#104067 (33054827), No reset autoCommit after unknown issue occurs.
1 parent bc45d35 commit 4d19ea1

File tree

3 files changed

+78
-2
lines changed

3 files changed

+78
-2
lines changed

CHANGES

+3
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33

44
Version 8.0.28
55

6+
- Fix for Bug#104067 (33054827), No reset autoCommit after unknown issue occurs.
7+
Thanks to Tingyu Wei for his contribution.
8+
69
- Fix for Bug#85223 (25656020), MYSQLSQLXML SETSTRING CRASH.
710

811
- Fix for Bug#84365 (33425867), INSERT..VALUE with VALUES function lead to a StringIndexOutOfBoundsException.

src/main/user-impl/java/com/mysql/cj/jdbc/ConnectionImpl.java

+10-2
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@
7070
import com.mysql.cj.conf.PropertyDefinitions.DatabaseTerm;
7171
import com.mysql.cj.conf.PropertyKey;
7272
import com.mysql.cj.conf.RuntimeProperty;
73+
import com.mysql.cj.exceptions.CJCommunicationsException;
7374
import com.mysql.cj.exceptions.CJException;
7475
import com.mysql.cj.exceptions.ExceptionFactory;
7576
import com.mysql.cj.exceptions.ExceptionInterceptor;
@@ -2017,10 +2018,10 @@ void forEach(ConnectionLifecycleInterceptor each) throws SQLException {
20172018
this.autoReconnect.setValue(true);
20182019
}
20192020

2021+
boolean isAutocommit = this.session.getServerSession().isAutocommit();
20202022
try {
20212023
boolean needsSetOnServer = true;
2022-
2023-
if (this.useLocalSessionState.getValue() && this.session.getServerSession().isAutoCommit() == autoCommitFlag) {
2024+
if (this.useLocalSessionState.getValue() && isAutocommit == autoCommitFlag) {
20242025
needsSetOnServer = false;
20252026
} else if (!this.autoReconnect.getValue()) {
20262027
needsSetOnServer = getSession().isSetNeededForAutoCommitMode(autoCommitFlag);
@@ -2035,6 +2036,13 @@ void forEach(ConnectionLifecycleInterceptor each) throws SQLException {
20352036
this.session.execSQL(null, autoCommitFlag ? "SET autocommit=1" : "SET autocommit=0", -1, null, false, this.nullStatementResultSetFactory,
20362037
null, false);
20372038
}
2039+
} catch (CJCommunicationsException e) {
2040+
throw e;
2041+
} catch (CJException e) {
2042+
// Reset to current autocommit value in case of an exception different than a communication exception occurs.
2043+
this.session.getServerSession().setAutoCommit(isAutocommit);
2044+
// Update the stacktrace.
2045+
throw SQLError.createSQLException(e.getMessage(), e.getSQLState(), e.getVendorCode(), e.isTransient(), e, getExceptionInterceptor());
20382046
} finally {
20392047
if (this.autoReconnectForPools.getValue()) {
20402048
this.autoReconnect.setValue(false);

src/test/java/testsuite/regression/ConnectionRegressionTest.java

+65
Original file line numberDiff line numberDiff line change
@@ -11562,4 +11562,69 @@ public void testBug28725534() throws Exception {
1156211562

1156311563
assertTrue(end - start < 250, ".equals() took too long to exectute, the method is being locked by a synchronized block.");
1156411564
}
11565+
11566+
/**
11567+
* Tests fix for Bug#104067 (33054827), No reset autoCommit after unknown issue occurs.
11568+
*
11569+
* @throws Exception
11570+
*/
11571+
@Test
11572+
public void testBug104067() throws Exception {
11573+
Properties props = new Properties();
11574+
props.setProperty(PropertyKey.sslMode.getKeyName(), SslMode.DISABLED.name());
11575+
props.setProperty(PropertyKey.allowPublicKeyRetrieval.getKeyName(), "true");
11576+
props.setProperty(PropertyKey.queryInterceptors.getKeyName(), Bug104067QueryInterceptor.class.getName());
11577+
Connection testConn = getConnectionWithProps(props);
11578+
Statement testStmt = testConn.createStatement();
11579+
11580+
// Connection vs session autocommit value:
11581+
// 1. Default value.
11582+
assertTrue(testConn.getAutoCommit());
11583+
this.rs = testStmt.executeQuery("SHOW SESSION VARIABLES LIKE 'autocommit'");
11584+
assertTrue(this.rs.next());
11585+
assertTrue(this.rs.getString(2).equalsIgnoreCase("ON"));
11586+
11587+
// 2. After Connection.setAutcommit(true).
11588+
try {
11589+
testConn.setAutoCommit(true);
11590+
} catch (SQLException e) {
11591+
fail("Exception not expected.", e);
11592+
}
11593+
assertTrue(testConn.getAutoCommit());
11594+
this.rs = testStmt.executeQuery("SHOW SESSION VARIABLES LIKE 'autocommit'");
11595+
assertTrue(this.rs.next());
11596+
assertTrue(this.rs.getString(2).equalsIgnoreCase("ON"));
11597+
11598+
// 3. After Connection.setAutcommit(false).
11599+
assertThrows(SQLException.class, () -> {
11600+
testConn.setAutoCommit(false);
11601+
return null;
11602+
});
11603+
assertTrue(testConn.getAutoCommit());
11604+
this.rs = testStmt.executeQuery("SHOW SESSION VARIABLES LIKE 'autocommit'");
11605+
this.rs.next();
11606+
assertTrue(this.rs.getString(2).equalsIgnoreCase("ON"));
11607+
11608+
// 4. After Connection.setAutcommit(true).
11609+
try {
11610+
testConn.setAutoCommit(true);
11611+
} catch (SQLException e) {
11612+
fail("Exception not expected.", e);
11613+
}
11614+
assertTrue(testConn.getAutoCommit());
11615+
this.rs = testStmt.executeQuery("SHOW SESSION VARIABLES LIKE 'autocommit'");
11616+
assertTrue(this.rs.next());
11617+
assertTrue(this.rs.getString(2).equalsIgnoreCase("ON"));
11618+
}
11619+
11620+
public static class Bug104067QueryInterceptor extends BaseQueryInterceptor {
11621+
@Override
11622+
public <T extends Resultset> T preProcess(Supplier<String> str, Query interceptedQuery) {
11623+
String sql = str.get();
11624+
if (sql.equalsIgnoreCase("SET autocommit=0")) {
11625+
throw ExceptionFactory.createException("Artificial non-connection related exception while executing \"" + sql + "\"");
11626+
}
11627+
return super.preProcess(str, interceptedQuery);
11628+
}
11629+
}
1156511630
}

0 commit comments

Comments
 (0)