Skip to content

Commit 06a7ec0

Browse files
committed
use query comment or connection attributes to provide driver metadata
1 parent 55c9022 commit 06a7ec0

20 files changed

+313
-301
lines changed

wrapper/src/main/java/software/amazon/jdbc/ConnectionPluginChainBuilder.java

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,34 @@ public class ConnectionPluginChainBuilder {
9191
}
9292
};
9393

94+
protected static final Map<String /* clazz */, String> pluginCodeByPlugin =
95+
new HashMap<String, String>() {
96+
{
97+
put("software.amazon.jdbc.plugin.ExecutionTimeConnectionPlugin", "executionTime");
98+
put("software.amazon.jdbc.plugin.LogQueryConnectionPlugin", "logQuery");
99+
put("software.amazon.jdbc.plugin.DataCacheConnectionPlugin", "dataCache");
100+
put("software.amazon.jdbc.plugin.customendpoint.CustomEndpointPlugin", "customEndpoint");
101+
put("software.amazon.jdbc.plugin.efm.HostMonitoringConnectionPlugin", "efm");
102+
put("software.amazon.jdbc.plugin.efm2.HostMonitoringConnectionPlugin", "efm2");
103+
put("software.amazon.jdbc.plugin.failover.FailoverConnectionPlugin", "failover");
104+
put("software.amazon.jdbc.plugin.failover2.FailoverConnectionPlugin", "failover2");
105+
put("software.amazon.jdbc.plugin.iam.IamAuthConnectionPlugin", "iam");
106+
put("software.amazon.jdbc.plugin.AwsSecretsManagerConnectionPlugin", "awsSecretsManager");
107+
put("software.amazon.jdbc.plugin.federatedauth.FederatedAuthPlugin", "federatedAuth");
108+
put("software.amazon.jdbc.plugin.federatedauth.OktaAuthPlugin", "okta");
109+
put("software.amazon.jdbc.plugin.staledns.AuroraStaleDnsPlugin", "auroraStaleDns");
110+
put("software.amazon.jdbc.plugin.readwritesplitting.ReadWriteSplittingPlugin", "readWriteSplitting");
111+
put("software.amazon.jdbc.plugin.AuroraConnectionTrackerPlugin", "auroraConnectionTracker");
112+
put("software.amazon.jdbc.plugin.DriverMetaDataConnectionPlugin", "driverMetaData");
113+
put("software.amazon.jdbc.plugin.ConnectTimeConnectionPlugin", "connectTime");
114+
put("software.amazon.jdbc.plugin.dev.DeveloperConnectionPlugin", "dev");
115+
put("software.amazon.jdbc.plugin.strategy.fastestresponse.FastestResponseStrategyPlugin",
116+
"fastestResponseStrategy");
117+
put("software.amazon.jdbc.plugin.AuroraInitialConnectionStrategyPlugin", "initialConnection");
118+
put("software.amazon.jdbc.plugin.limitless.LimitlessConnectionPlugin", "limitless");
119+
}
120+
};
121+
94122
/**
95123
* The final list of plugins will be sorted by weight, starting from the lowest values up to
96124
* the highest values. The first plugin of the list will have the lowest weight, and the
@@ -189,7 +217,7 @@ public List<ConnectionPlugin> getPlugins(
189217
}
190218
} else {
191219

192-
final List<String> pluginCodeList = getPluginCodes(props);
220+
final List<String> pluginCodeList = this.getPluginCodes(props);
193221
pluginFactories = new ArrayList<>(pluginCodeList.size());
194222

195223
for (final String pluginCode : pluginCodeList) {
@@ -242,14 +270,23 @@ public List<ConnectionPlugin> getPlugins(
242270
return plugins;
243271
}
244272

245-
public static List<String> getPluginCodes(final Properties props) {
273+
public List<String> getPluginCodes(final Properties props) {
246274
String pluginCodes = PropertyDefinition.PLUGINS.getString(props);
247275
if (pluginCodes == null) {
248276
pluginCodes = DEFAULT_PLUGINS;
249277
}
250278
return StringUtils.split(pluginCodes, ",", true);
251279
}
252280

281+
public String getPluginCodes(final List<ConnectionPlugin> plugins) {
282+
return plugins.stream()
283+
.filter(x -> !(x instanceof DefaultConnectionPlugin))
284+
.map(x -> pluginCodeByPlugin.getOrDefault(x.getClass().getName(), "unknown"))
285+
.distinct()
286+
.sorted()
287+
.collect(Collectors.joining("+"));
288+
}
289+
253290
protected List<ConnectionPluginFactory> sortPluginFactories(
254291
final List<ConnectionPluginFactory> unsortedPluginFactories) {
255292

wrapper/src/main/java/software/amazon/jdbc/ConnectionPluginManager.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,7 @@ public class ConnectionPluginManager implements CanReleaseResources, Wrapper {
9797

9898
protected Properties props = new Properties();
9999
protected List<ConnectionPlugin> plugins;
100+
protected String effectivePluginCodes;
100101
protected final @NonNull ConnectionProvider defaultConnProvider;
101102
protected final @Nullable ConnectionProvider effectiveConnProvider;
102103
protected final ConnectionWrapper connectionWrapper;
@@ -197,6 +198,8 @@ public void init(
197198
pluginManagerService,
198199
props,
199200
configurationProfile);
201+
this.effectivePluginCodes = pluginChainBuilder.getPluginCodes(this.plugins);
202+
this.props.setProperty(EFFECTIVE_PLUGIN_CODES_PROPERTY, this.effectivePluginCodes);
200203
}
201204

202205
protected <T, E extends Exception> T executeWithSubscribedPlugins(

wrapper/src/main/java/software/amazon/jdbc/PluginServiceImpl.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -725,7 +725,8 @@ public void updateDialect(final @NonNull Connection connection) throws SQLExcept
725725
this.dialect = this.dialectProvider.getDialect(
726726
this.originalUrl,
727727
this.initialConnectionHostSpec,
728-
connection);
728+
connection,
729+
this.props);
729730
if (originalDialect == this.dialect) {
730731
return;
731732
}

wrapper/src/main/java/software/amazon/jdbc/PropertyDefinition.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -247,6 +247,7 @@ public static void removeAllExceptCredentials(final Properties props) {
247247
final String password = props.getProperty(PropertyDefinition.PASSWORD.name, null);
248248

249249
removeAll(props);
250+
props.remove(ConnectionPluginManager.EFFECTIVE_PLUGIN_CODES_PROPERTY);
250251

251252
if (user != null) {
252253
props.setProperty(PropertyDefinition.USER.name, user);

wrapper/src/main/java/software/amazon/jdbc/dialect/AuroraMysqlDialect.java

Lines changed: 14 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
import java.util.Collections;
2424
import java.util.List;
2525
import software.amazon.jdbc.PluginService;
26+
import java.util.Properties;
2627
import software.amazon.jdbc.hostlistprovider.AuroraHostListProvider;
2728
import software.amazon.jdbc.hostlistprovider.monitoring.MonitoringRdsHostListProvider;
2829
import software.amazon.jdbc.plugin.failover2.FailoverConnectionPlugin;
@@ -51,33 +52,22 @@ public class AuroraMysqlDialect extends MysqlDialect implements BlueGreenDialect
5152
+ " table_schema = 'mysql' AND table_name = 'rds_topology'";
5253

5354
@Override
54-
public boolean isDialect(final Connection connection) {
55-
Statement stmt = null;
56-
ResultSet rs = null;
55+
public boolean isDialect(final Connection connection, final Properties properties) {
56+
if (super.isDialect(connection, properties)) {
57+
// If super.isDialect() returns true then there is no need to check other conditions.
58+
return false;
59+
}
60+
5761
try {
58-
stmt = connection.createStatement();
59-
rs = stmt.executeQuery("SHOW VARIABLES LIKE 'aurora_version'");
60-
if (rs.next()) {
61-
// If variable with such name is presented then it means it's an Aurora cluster
62-
return true;
63-
}
64-
} catch (final SQLException ex) {
65-
// ignore
66-
} finally {
67-
if (stmt != null) {
68-
try {
69-
stmt.close();
70-
} catch (SQLException ex) {
71-
// ignore
72-
}
73-
}
74-
if (rs != null) {
75-
try {
76-
rs.close();
77-
} catch (SQLException ex) {
78-
// ignore
62+
try (Statement stmt = connection.createStatement();
63+
ResultSet rs = stmt.executeQuery("SHOW VARIABLES LIKE 'aurora_version'")) {
64+
if (rs.next()) {
65+
// If variable with such name is presented then it means it's an Aurora cluster
66+
return true;
7967
}
8068
}
69+
} catch (SQLException ex) {
70+
// do nothing
8171
}
8272
return false;
8373
}

wrapper/src/main/java/software/amazon/jdbc/dialect/AuroraPgDialect.java

Lines changed: 20 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
import java.sql.ResultSet;
2121
import java.sql.SQLException;
2222
import java.sql.Statement;
23+
import java.util.Properties;
2324
import java.util.logging.Logger;
2425
import software.amazon.jdbc.PluginService;
2526
import software.amazon.jdbc.hostlistprovider.AuroraHostListProvider;
@@ -65,72 +66,36 @@ public class AuroraPgDialect extends PgDialect implements AuroraLimitlessDialect
6566
"SELECT 'get_blue_green_fast_switchover_metadata'::regproc";
6667

6768
@Override
68-
public boolean isDialect(final Connection connection) {
69-
if (!super.isDialect(connection)) {
69+
public boolean isDialect(final Connection connection, final Properties properties) {
70+
if (!super.isDialect(connection, properties)) {
7071
return false;
7172
}
7273

73-
Statement stmt = null;
74-
ResultSet rs = null;
75-
boolean hasExtensions = false;
76-
boolean hasTopology = false;
7774
try {
78-
stmt = connection.createStatement();
79-
rs = stmt.executeQuery(extensionsSql);
80-
if (rs.next()) {
75+
try (Statement stmt = connection.createStatement();
76+
ResultSet rs = stmt.executeQuery(extensionsSql)) {
77+
if (!rs.next()) {
78+
return false;
79+
}
8180
final boolean auroraUtils = rs.getBoolean("aurora_stat_utils");
8281
LOGGER.finest(() -> String.format("auroraUtils: %b", auroraUtils));
83-
if (auroraUtils) {
84-
hasExtensions = true;
85-
}
86-
}
87-
} catch (SQLException ex) {
88-
// ignore
89-
} finally {
90-
if (stmt != null) {
91-
try {
92-
stmt.close();
93-
} catch (SQLException ex) {
94-
// ignore
82+
if (!auroraUtils) {
83+
return false;
9584
}
9685
}
97-
if (rs != null) {
98-
try {
99-
rs.close();
100-
} catch (SQLException ex) {
101-
// ignore
102-
}
103-
}
104-
}
105-
if (!hasExtensions) {
106-
return false;
107-
}
108-
try {
109-
stmt = connection.createStatement();
110-
rs = stmt.executeQuery(topologySql);
111-
if (rs.next()) {
112-
LOGGER.finest(() -> "hasTopology: true");
113-
hasTopology = true;
114-
}
115-
} catch (final SQLException ex) {
116-
// ignore
117-
} finally {
118-
if (stmt != null) {
119-
try {
120-
stmt.close();
121-
} catch (SQLException ex) {
122-
// ignore
123-
}
124-
}
125-
if (rs != null) {
126-
try {
127-
rs.close();
128-
} catch (SQLException ex) {
129-
// ignore
86+
87+
try (Statement stmt = connection.createStatement();
88+
ResultSet rs = stmt.executeQuery(topologySql)) {
89+
if (rs.next()) {
90+
LOGGER.finest(() -> "hasTopology: true");
91+
return true;
13092
}
93+
LOGGER.finest(() -> "hasTopology: false");
13194
}
95+
} catch (SQLException ex) {
96+
// do nothing
13297
}
133-
return hasExtensions && hasTopology;
98+
return false;
13499
}
135100

136101
@Override

wrapper/src/main/java/software/amazon/jdbc/dialect/Dialect.java

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -32,16 +32,23 @@ public interface Dialect {
3232

3333
String getHostAliasQuery();
3434

35-
String getServerVersionQuery();
35+
// The query should return two column:
36+
// - parameter name
37+
// - parameter value with a database version
38+
String getServerVersionQuery(final Properties properties);
3639

37-
boolean isDialect(Connection connection);
40+
boolean isDialect(final Connection connection, final Properties properties);
3841

3942
List</* dialect code */ String> getDialectUpdateCandidates();
4043

4144
HostListProviderSupplier getHostListProvider();
4245

4346
void prepareConnectProperties(
44-
final @NonNull Properties connectProperties, final @NonNull String protocol, final @NonNull HostSpec hostSpec);
47+
final @NonNull Properties connectProperties,
48+
final @NonNull String protocol,
49+
final @NonNull HostSpec hostSpec);
4550

4651
EnumSet<FailoverRestriction> getFailoverRestrictions();
52+
53+
void reportMetadata(final @NonNull Connection connection, final @NonNull Properties properties);
4754
}

wrapper/src/main/java/software/amazon/jdbc/dialect/DialectManager.java

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@ public class DialectManager implements DialectProvider {
7979
private final RdsUtils rdsHelper = new RdsUtils();
8080
private final ConnectionUrlParser connectionUrlParser = new ConnectionUrlParser();
8181
private boolean canUpdate = false;
82+
private boolean shouldReportMetadata = false;
8283
private Dialect dialect = null;
8384
private String dialectCode;
8485

@@ -133,6 +134,7 @@ public Dialect getDialect(
133134
this.dialectCode = DialectCodes.CUSTOM;
134135
this.dialect = customDialect;
135136
this.logCurrentDialect();
137+
this.shouldReportMetadata = true;
136138
return this.dialect;
137139
}
138140

@@ -147,6 +149,7 @@ public Dialect getDialect(
147149
this.dialectCode = dialectCode;
148150
this.dialect = userDialect;
149151
this.logCurrentDialect();
152+
this.shouldReportMetadata = true;
150153
return userDialect;
151154
} else {
152155
throw new SQLException(
@@ -234,10 +237,15 @@ public Dialect getDialect(
234237
public Dialect getDialect(
235238
final @NonNull String originalUrl,
236239
final @NonNull HostSpec hostSpec,
237-
final @NonNull Connection connection) throws SQLException {
240+
final @NonNull Connection connection,
241+
final @NonNull Properties properties) throws SQLException {
238242

239243
if (!this.canUpdate) {
240244
this.logCurrentDialect();
245+
if (this.shouldReportMetadata) {
246+
this.dialect.reportMetadata(connection, properties);
247+
this.shouldReportMetadata = false;
248+
}
241249
return this.dialect;
242250
}
243251

@@ -249,7 +257,7 @@ public Dialect getDialect(
249257
throw new SQLException(
250258
Messages.get("DialectManager.unknownDialectCode", new Object[] {dialectCandidateCode}));
251259
}
252-
boolean isDialect = dialectCandidate.isDialect(connection);
260+
boolean isDialect = dialectCandidate.isDialect(connection, properties);
253261
if (isDialect) {
254262
this.canUpdate = false;
255263
this.dialectCode = dialectCandidateCode;

wrapper/src/main/java/software/amazon/jdbc/dialect/DialectProvider.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,5 +31,6 @@ Dialect getDialect(
3131
Dialect getDialect(
3232
final @NonNull String originalUrl,
3333
final @NonNull HostSpec hostSpec,
34-
final @NonNull Connection connection) throws SQLException;
34+
final @NonNull Connection connection,
35+
final @NonNull Properties properties) throws SQLException;
3536
}

0 commit comments

Comments
 (0)