diff options
author | Jacek <jacek.poreda@sonarsource.com> | 2022-02-10 12:09:48 +0100 |
---|---|---|
committer | sonartech <sonartech@sonarsource.com> | 2022-08-29 20:02:52 +0000 |
commit | 8961d0c0b80dd23b7ed01ea0f249282956374795 (patch) | |
tree | fb1ab3db4f1fdd2c27b6ba1398a06572822a1b25 /server/sonar-db-core/src | |
parent | 4d1bd03543c55e564151d55e3a4763b82bc8e512 (diff) | |
download | sonarqube-8961d0c0b80dd23b7ed01ea0f249282956374795.tar.gz sonarqube-8961d0c0b80dd23b7ed01ea0f249282956374795.zip |
SONAR-17200 Move to HikariCP from Apache DBCP
Diffstat (limited to 'server/sonar-db-core/src')
9 files changed, 339 insertions, 389 deletions
diff --git a/server/sonar-db-core/src/main/java/org/sonar/db/DefaultDatabase.java b/server/sonar-db-core/src/main/java/org/sonar/db/DefaultDatabase.java index be9cd2b872c..837b941f445 100644 --- a/server/sonar-db-core/src/main/java/org/sonar/db/DefaultDatabase.java +++ b/server/sonar-db-core/src/main/java/org/sonar/db/DefaultDatabase.java @@ -21,15 +21,15 @@ package org.sonar.db; import ch.qos.logback.classic.Level; import com.google.common.annotations.VisibleForTesting; -import com.google.common.collect.ImmutableMap; +import com.zaxxer.hikari.HikariConfig; +import com.zaxxer.hikari.HikariDataSource; import java.sql.Connection; import java.sql.SQLException; import java.util.List; import java.util.Map; import java.util.Properties; +import java.util.Set; import javax.sql.DataSource; -import org.apache.commons.dbcp2.BasicDataSource; -import org.apache.commons.dbcp2.BasicDataSourceFactory; import org.apache.commons.lang.StringUtils; import org.sonar.api.config.internal.Settings; import org.sonar.api.utils.log.Logger; @@ -43,7 +43,12 @@ import org.sonar.process.logging.LogbackHelper; import static com.google.common.base.Preconditions.checkState; import static java.lang.String.format; +import static org.sonar.process.ProcessProperties.Property.JDBC_DRIVER_PATH; +import static org.sonar.process.ProcessProperties.Property.JDBC_EMBEDDED_PORT; +import static org.sonar.process.ProcessProperties.Property.JDBC_MIN_IDLE; +import static org.sonar.process.ProcessProperties.Property.JDBC_PASSWORD; import static org.sonar.process.ProcessProperties.Property.JDBC_URL; +import static org.sonar.process.ProcessProperties.Property.JDBC_USERNAME; /** * @since 2.12 @@ -57,12 +62,25 @@ public class DefaultDatabase implements Database { private static final String SONAR_JDBC_DIALECT = "sonar.jdbc.dialect"; private static final String SONAR_JDBC_DRIVER = "sonar.jdbc.driverClassName"; private static final String SONAR_JDBC_MAX_ACTIVE = "sonar.jdbc.maxActive"; - private static final String DBCP_JDBC_MAX_ACTIVE = "maxTotal"; private static final String SONAR_JDBC_MAX_WAIT = "sonar.jdbc.maxWait"; - private static final String DBCP_JDBC_MAX_WAIT = "maxWaitMillis"; - private static final Map<String, String> SONAR_JDBC_TO_DBCP_PROPERTY_MAPPINGS = ImmutableMap.of( - SONAR_JDBC_MAX_ACTIVE, DBCP_JDBC_MAX_ACTIVE, - SONAR_JDBC_MAX_WAIT, DBCP_JDBC_MAX_WAIT); + private static final Set<String> DEPRECATED_SONAR_PROPERTIES = Set.of( + "sonar.jdbc.maxIdle", + "sonar.jdbc.minEvictableIdleTimeMillis", + "sonar.jdbc.timeBetweenEvictionRunsMillis"); + + private static final Set<String> IGNORED_SONAR_PROPERTIES = Set.of(SONAR_JDBC_DIALECT, JDBC_DRIVER_PATH.getKey(), + "sonar.jdbc.maxIdle", + "sonar.jdbc.minEvictableIdleTimeMillis", + "sonar.jdbc.timeBetweenEvictionRunsMillis"); + + private static final Map<String, String> SONAR_JDBC_TO_HIKARI_PROPERTY_MAPPINGS = Map.of( + JDBC_USERNAME.getKey(), "dataSource.user", + JDBC_PASSWORD.getKey(), "dataSource.password", + JDBC_EMBEDDED_PORT.getKey(), "dataSource.portNumber", + JDBC_URL.getKey(), "jdbcUrl", + SONAR_JDBC_MAX_WAIT, "connectionTimeout", + SONAR_JDBC_MAX_ACTIVE, "maximumPoolSize", + JDBC_MIN_IDLE.getKey(), "minimumIdle"); private final LogbackHelper logbackHelper; private final Settings settings; @@ -99,16 +117,22 @@ public class DefaultDatabase implements Database { properties.setProperty(SONAR_JDBC_DRIVER, dialect.getDefaultDriverClassName()); } - private void initDataSource() throws Exception { - // but it's correctly caught by start() - LOG.info("Create JDBC data source for {}", properties.getProperty(JDBC_URL.getKey()), DEFAULT_URL); - BasicDataSource basicDataSource = BasicDataSourceFactory.createDataSource(extractCommonsDbcpProperties(properties)); - datasource = new ProfiledDataSource(basicDataSource, NullConnectionInterceptor.INSTANCE); - datasource.setConnectionInitSqls(dialect.getConnectionInitStatements()); - datasource.setValidationQuery(dialect.getValidationQuery()); + private void initDataSource() { + LOG.info("Create JDBC data source for {}", properties.getProperty(JDBC_URL.getKey(), DEFAULT_URL)); + HikariDataSource ds = createHikariDataSource(); + datasource = new ProfiledDataSource(ds, NullConnectionInterceptor.INSTANCE); enableSqlLogging(datasource, logbackHelper.getLoggerLevel("sql") == Level.TRACE); } + private HikariDataSource createHikariDataSource() { + HikariConfig config = new HikariConfig(extractCommonsHikariProperties(properties)); + if (!dialect.getConnectionInitStatements().isEmpty()) { + config.setConnectionInitSql(dialect.getConnectionInitStatements().get(0)); + } + config.setConnectionTestQuery(dialect.getValidationQuery()); + return new HikariDataSource(config); + } + private void checkConnection() { Connection connection = null; try { @@ -124,11 +148,7 @@ public class DefaultDatabase implements Database { @Override public void stop() { if (datasource != null) { - try { - datasource.close(); - } catch (SQLException e) { - throw new IllegalStateException("Fail to stop JDBC connection pool", e); - } + datasource.close(); } } @@ -171,17 +191,22 @@ public class DefaultDatabase implements Database { } @VisibleForTesting - static Properties extractCommonsDbcpProperties(Properties properties) { + static Properties extractCommonsHikariProperties(Properties properties) { Properties result = new Properties(); - result.setProperty("accessToUnderlyingConnectionAllowed", "true"); for (Map.Entry<Object, Object> entry : properties.entrySet()) { String key = (String) entry.getKey(); + if (IGNORED_SONAR_PROPERTIES.contains(key)) { + if (DEPRECATED_SONAR_PROPERTIES.contains(key)) { + LOG.warn("Property [{}] has no effect as pool connection implementation changed, check 9.7 upgrade notes.", key); + } + continue; + } if (StringUtils.startsWith(key, SONAR_JDBC)) { - String resolvedKey = toDbcpPropertyKey(key); + String resolvedKey = toHikariPropertyKey(key); String existingValue = (String) result.setProperty(resolvedKey, (String) entry.getValue()); checkState(existingValue == null || existingValue.equals(entry.getValue()), "Duplicate property declaration for resolved jdbc key '%s': conflicting values are '%s' and '%s'", resolvedKey, existingValue, entry.getValue()); - result.setProperty(toDbcpPropertyKey(key), (String) entry.getValue()); + result.setProperty(resolvedKey, (String) entry.getValue()); } } return result; @@ -193,9 +218,9 @@ public class DefaultDatabase implements Database { } } - private static String toDbcpPropertyKey(String key) { - if (SONAR_JDBC_TO_DBCP_PROPERTY_MAPPINGS.containsKey(key)) { - return SONAR_JDBC_TO_DBCP_PROPERTY_MAPPINGS.get(key); + private static String toHikariPropertyKey(String key) { + if (SONAR_JDBC_TO_HIKARI_PROPERTY_MAPPINGS.containsKey(key)) { + return SONAR_JDBC_TO_HIKARI_PROPERTY_MAPPINGS.get(key); } return StringUtils.removeStart(key, SONAR_JDBC); diff --git a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ConnectionInterceptor.java b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ConnectionInterceptor.java index 1a856ca23ce..650405c19c5 100644 --- a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ConnectionInterceptor.java +++ b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ConnectionInterceptor.java @@ -21,12 +21,12 @@ package org.sonar.db.profiling; import java.sql.Connection; import java.sql.SQLException; -import org.apache.commons.dbcp2.BasicDataSource; +import javax.sql.DataSource; public interface ConnectionInterceptor { - Connection getConnection(BasicDataSource dataSource) throws SQLException; + Connection getConnection(DataSource dataSource) throws SQLException; - Connection getConnection(BasicDataSource dataSource, String login, String password) throws SQLException; + Connection getConnection(DataSource dataSource, String login, String password) throws SQLException; } diff --git a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/NullConnectionInterceptor.java b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/NullConnectionInterceptor.java index 9e069ccb408..c8d4d3b2915 100644 --- a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/NullConnectionInterceptor.java +++ b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/NullConnectionInterceptor.java @@ -21,18 +21,18 @@ package org.sonar.db.profiling; import java.sql.Connection; import java.sql.SQLException; -import org.apache.commons.dbcp2.BasicDataSource; +import javax.sql.DataSource; public enum NullConnectionInterceptor implements ConnectionInterceptor { INSTANCE; @Override - public Connection getConnection(BasicDataSource dataSource) throws SQLException { + public Connection getConnection(DataSource dataSource) throws SQLException { return dataSource.getConnection(); } @Override - public Connection getConnection(BasicDataSource dataSource, String user, String password) throws SQLException { + public Connection getConnection(DataSource dataSource, String user, String password) throws SQLException { return dataSource.getConnection(user, password); } } diff --git a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledConnectionInterceptor.java b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledConnectionInterceptor.java index 43f79c54c68..b2c384f3572 100644 --- a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledConnectionInterceptor.java +++ b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledConnectionInterceptor.java @@ -22,18 +22,18 @@ package org.sonar.db.profiling; import java.lang.reflect.Proxy; import java.sql.Connection; import java.sql.SQLException; -import org.apache.commons.dbcp2.BasicDataSource; +import javax.sql.DataSource; public enum ProfiledConnectionInterceptor implements ConnectionInterceptor { INSTANCE; @Override - public Connection getConnection(BasicDataSource dataSource) throws SQLException { + public Connection getConnection(DataSource dataSource) throws SQLException { return buildConnectionProxy(new ProfilingConnectionHandler(dataSource.getConnection())); } @Override - public Connection getConnection(BasicDataSource dataSource, String login, String password) throws SQLException { + public Connection getConnection(DataSource dataSource, String login, String password) throws SQLException { return buildConnectionProxy(new ProfilingConnectionHandler(dataSource.getConnection(login, password))); } diff --git a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledDataSource.java b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledDataSource.java index 579a4dc2bea..410aecb0e7a 100644 --- a/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledDataSource.java +++ b/server/sonar-db-core/src/main/java/org/sonar/db/profiling/ProfiledDataSource.java @@ -19,32 +19,37 @@ */ package org.sonar.db.profiling; +import com.zaxxer.hikari.HikariConfig; +import com.zaxxer.hikari.HikariConfigMXBean; +import com.zaxxer.hikari.HikariDataSource; +import com.zaxxer.hikari.HikariPoolMXBean; +import com.zaxxer.hikari.metrics.MetricsTrackerFactory; import java.io.PrintWriter; import java.sql.Connection; -import java.sql.Driver; +import java.sql.ConnectionBuilder; import java.sql.SQLException; -import java.util.Collection; -import java.util.List; -import java.util.Set; -import javax.management.MBeanServer; -import javax.management.ObjectName; -import org.apache.commons.dbcp2.BasicDataSource; +import java.sql.SQLFeatureNotSupportedException; +import java.sql.ShardingKeyBuilder; +import java.util.Properties; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ThreadFactory; +import javax.sql.DataSource; import org.sonar.api.utils.log.Logger; import org.sonar.api.utils.log.Loggers; -public class ProfiledDataSource extends BasicDataSource { +public class ProfiledDataSource extends HikariDataSource { static final Logger SQL_LOGGER = Loggers.get("sql"); - private final BasicDataSource delegate; + private final HikariDataSource delegate; private ConnectionInterceptor connectionInterceptor; - public ProfiledDataSource(BasicDataSource delegate, ConnectionInterceptor connectionInterceptor) { + public ProfiledDataSource(HikariDataSource delegate, ConnectionInterceptor connectionInterceptor) { this.delegate = delegate; this.connectionInterceptor = connectionInterceptor; } - public BasicDataSource getDelegate() { + public HikariDataSource getDelegate() { return delegate; } @@ -53,33 +58,33 @@ public class ProfiledDataSource extends BasicDataSource { } @Override - public Boolean getDefaultAutoCommit() { - return delegate.getDefaultAutoCommit(); + public boolean isAutoCommit() { + return delegate.isAutoCommit(); } @Override - public Boolean getDefaultReadOnly() { - return delegate.getDefaultReadOnly(); + public boolean isReadOnly() { + return delegate.isReadOnly(); } @Override - public int getDefaultTransactionIsolation() { - return delegate.getDefaultTransactionIsolation(); + public String getTransactionIsolation() { + return delegate.getTransactionIsolation(); } @Override - public void setDefaultTransactionIsolation(int defaultTransactionIsolation) { - delegate.setDefaultTransactionIsolation(defaultTransactionIsolation); + public void setTransactionIsolation(String defaultTransactionIsolation) { + delegate.setTransactionIsolation(defaultTransactionIsolation); } @Override - public String getDefaultCatalog() { - return delegate.getDefaultCatalog(); + public String getCatalog() { + return delegate.getCatalog(); } @Override - public void setDefaultCatalog(String defaultCatalog) { - delegate.setDefaultCatalog(defaultCatalog); + public void setCatalog(String defaultCatalog) { + delegate.setCatalog(defaultCatalog); } @Override @@ -93,153 +98,158 @@ public class ProfiledDataSource extends BasicDataSource { } @Override - public synchronized ClassLoader getDriverClassLoader() { - return delegate.getDriverClassLoader(); + public int getMaximumPoolSize() { + return delegate.getMaximumPoolSize(); } @Override - public synchronized void setDriverClassLoader(ClassLoader driverClassLoader) { - delegate.setDriverClassLoader(driverClassLoader); + public void setMaximumPoolSize(int maxActive) { + delegate.setMaximumPoolSize(maxActive); } @Override - public synchronized int getMaxTotal() { - return delegate.getMaxTotal(); + public Connection getConnection() throws SQLException { + return connectionInterceptor.getConnection(delegate); } @Override - public synchronized void setMaxTotal(int maxActive) { - delegate.setMaxTotal(maxActive); + public Connection getConnection(String login, String password) throws SQLException { + return connectionInterceptor.getConnection(this, login, password); } @Override - public synchronized int getMaxIdle() { - return delegate.getMaxIdle(); + public PrintWriter getLogWriter() throws SQLException { + return delegate.getLogWriter(); } @Override - public synchronized void setMaxIdle(int maxIdle) { - delegate.setMaxIdle(maxIdle); + public void setLogWriter(PrintWriter out) throws SQLException { + delegate.setLogWriter(out); } @Override - public synchronized int getMinIdle() { - return delegate.getMinIdle(); + public void setLoginTimeout(int seconds) throws SQLException { + delegate.setLoginTimeout(seconds); } @Override - public synchronized void setMinIdle(int minIdle) { - delegate.setMinIdle(minIdle); + public int getLoginTimeout() throws SQLException { + return delegate.getLoginTimeout(); } @Override - public synchronized int getInitialSize() { - return delegate.getInitialSize(); + public java.util.logging.Logger getParentLogger() throws SQLFeatureNotSupportedException { + return delegate.getParentLogger(); } @Override - public synchronized void setInitialSize(int initialSize) { - delegate.setInitialSize(initialSize); + public <T> T unwrap(Class<T> iface) throws SQLException { + return delegate.unwrap(iface); } @Override - public synchronized long getMaxWaitMillis() { - return delegate.getMaxWaitMillis(); + public boolean isWrapperFor(Class<?> iface) throws SQLException { + return delegate.isWrapperFor(iface); } @Override - public synchronized void setMaxWaitMillis(long maxWait) { - delegate.setMaxWaitMillis(maxWait); + public void setMetricRegistry(Object metricRegistry) { + delegate.setMetricRegistry(metricRegistry); } @Override - public synchronized boolean isPoolPreparedStatements() { - return delegate.isPoolPreparedStatements(); + public void setMetricsTrackerFactory(MetricsTrackerFactory metricsTrackerFactory) { + delegate.setMetricsTrackerFactory(metricsTrackerFactory); } @Override - public synchronized void setPoolPreparedStatements(boolean poolingStatements) { - delegate.setPoolPreparedStatements(poolingStatements); + public void setHealthCheckRegistry(Object healthCheckRegistry) { + delegate.setHealthCheckRegistry(healthCheckRegistry); } @Override - public synchronized int getMaxOpenPreparedStatements() { - return delegate.getMaxOpenPreparedStatements(); + public boolean isRunning() { + return delegate.isRunning(); } @Override - public synchronized void setMaxOpenPreparedStatements(int maxOpenStatements) { - delegate.setMaxOpenPreparedStatements(maxOpenStatements); + public HikariPoolMXBean getHikariPoolMXBean() { + return delegate.getHikariPoolMXBean(); } @Override - public synchronized boolean getTestOnBorrow() { - return delegate.getTestOnBorrow(); + public HikariConfigMXBean getHikariConfigMXBean() { + return delegate.getHikariConfigMXBean(); } @Override - public synchronized void setTestOnBorrow(boolean testOnBorrow) { - delegate.setTestOnBorrow(testOnBorrow); + public void evictConnection(Connection connection) { + delegate.evictConnection(connection); } @Override - public synchronized boolean getTestOnReturn() { - return delegate.getTestOnReturn(); + public void close() { + delegate.close(); } @Override - public synchronized void setTestOnReturn(boolean testOnReturn) { - delegate.setTestOnReturn(testOnReturn); + public boolean isClosed() { + return delegate.isClosed(); } @Override - public synchronized long getTimeBetweenEvictionRunsMillis() { - return delegate.getTimeBetweenEvictionRunsMillis(); + public String toString() { + return delegate.toString(); } @Override - public synchronized void setTimeBetweenEvictionRunsMillis(long timeBetweenEvictionRunsMillis) { - delegate.setTimeBetweenEvictionRunsMillis(timeBetweenEvictionRunsMillis); + public long getConnectionTimeout() { + return delegate.getConnectionTimeout(); } @Override - public synchronized int getNumTestsPerEvictionRun() { - return delegate.getNumTestsPerEvictionRun(); + public void setConnectionTimeout(long connectionTimeoutMs) { + delegate.setConnectionTimeout(connectionTimeoutMs); } @Override - public synchronized void setNumTestsPerEvictionRun(int numTestsPerEvictionRun) { - delegate.setNumTestsPerEvictionRun(numTestsPerEvictionRun); + public long getIdleTimeout() { + return delegate.getIdleTimeout(); } @Override - public synchronized long getMinEvictableIdleTimeMillis() { - return delegate.getMinEvictableIdleTimeMillis(); + public void setIdleTimeout(long idleTimeoutMs) { + delegate.setIdleTimeout(idleTimeoutMs); } @Override - public synchronized void setMinEvictableIdleTimeMillis(long minEvictableIdleTimeMillis) { - delegate.setMinEvictableIdleTimeMillis(minEvictableIdleTimeMillis); + public long getLeakDetectionThreshold() { + return delegate.getLeakDetectionThreshold(); } @Override - public synchronized boolean getTestWhileIdle() { - return delegate.getTestWhileIdle(); + public void setLeakDetectionThreshold(long leakDetectionThresholdMs) { + delegate.setLeakDetectionThreshold(leakDetectionThresholdMs); } @Override - public synchronized void setTestWhileIdle(boolean testWhileIdle) { - delegate.setTestWhileIdle(testWhileIdle); + public long getMaxLifetime() { + return delegate.getMaxLifetime(); } @Override - public synchronized int getNumActive() { - return delegate.getNumActive(); + public void setMaxLifetime(long maxLifetimeMs) { + delegate.setMaxLifetime(maxLifetimeMs); } @Override - public synchronized int getNumIdle() { - return delegate.getNumIdle(); + public int getMinimumIdle() { + return delegate.getMinimumIdle(); + } + + @Override + public void setMinimumIdle(int minIdle) { + delegate.setMinimumIdle(minIdle); } @Override @@ -253,16 +263,6 @@ public class ProfiledDataSource extends BasicDataSource { } @Override - public synchronized String getUrl() { - return delegate.getUrl(); - } - - @Override - public synchronized void setUrl(String url) { - delegate.setUrl(url); - } - - @Override public String getUsername() { return delegate.getUsername(); } @@ -273,368 +273,249 @@ public class ProfiledDataSource extends BasicDataSource { } @Override - public String getValidationQuery() { - return delegate.getValidationQuery(); - } - - @Override - public void setValidationQuery(String validationQuery) { - delegate.setValidationQuery(validationQuery); - } - - @Override - public int getValidationQueryTimeout() { - return delegate.getValidationQueryTimeout(); - } - - @Override - public void setValidationQueryTimeout(int timeout) { - delegate.setValidationQueryTimeout(timeout); - } - - @Override - public List<String> getConnectionInitSqls() { - return delegate.getConnectionInitSqls(); - } - - @Override - public void setConnectionInitSqls(Collection<String> connectionInitSqls) { - delegate.setConnectionInitSqls(connectionInitSqls); - } - - @Override - public synchronized boolean isAccessToUnderlyingConnectionAllowed() { - return delegate.isAccessToUnderlyingConnectionAllowed(); - } - - @Override - public synchronized void setAccessToUnderlyingConnectionAllowed(boolean allow) { - delegate.setAccessToUnderlyingConnectionAllowed(allow); - } - - @Override - public Connection getConnection() throws SQLException { - return connectionInterceptor.getConnection(delegate); - } - - @Override - public Connection getConnection(String login, String password) throws SQLException { - return connectionInterceptor.getConnection(this, login, password); - } - - @Override - public int getLoginTimeout() throws SQLException { - return delegate.getLoginTimeout(); - } - - @Override - public java.util.logging.Logger getParentLogger() { - return java.util.logging.Logger.getLogger(getClass().getName()); - } - - @Override - public PrintWriter getLogWriter() throws SQLException { - return delegate.getLogWriter(); - } - - @Override - public void setLoginTimeout(int loginTimeout) throws SQLException { - delegate.setLoginTimeout(loginTimeout); - } - - @Override - public void setLogWriter(PrintWriter logWriter) throws SQLException { - delegate.setLogWriter(logWriter); - } - - @Override - public boolean getRemoveAbandonedOnBorrow() { - return delegate.getRemoveAbandonedOnBorrow(); - } - - @Override - public void setRemoveAbandonedOnBorrow(boolean removeAbandoned) { - delegate.setRemoveAbandonedOnBorrow(removeAbandoned); - } - - - @Override - public boolean getRemoveAbandonedOnMaintenance() { - return delegate.getRemoveAbandonedOnMaintenance(); + public long getValidationTimeout() { + return delegate.getValidationTimeout(); } @Override - public void setRemoveAbandonedOnMaintenance(boolean removeAbandoned) { - delegate.setRemoveAbandonedOnMaintenance(removeAbandoned); + public void setValidationTimeout(long validationTimeoutMs) { + delegate.setValidationTimeout(validationTimeoutMs); } @Override - public int getRemoveAbandonedTimeout() { - return delegate.getRemoveAbandonedTimeout(); + public String getConnectionTestQuery() { + return delegate.getConnectionTestQuery(); } @Override - public void setRemoveAbandonedTimeout(int removeAbandonedTimeout) { - delegate.setRemoveAbandonedTimeout(removeAbandonedTimeout); + public void setConnectionTestQuery(String connectionTestQuery) { + delegate.setConnectionTestQuery(connectionTestQuery); } @Override - public boolean getLogAbandoned() { - return delegate.getLogAbandoned(); + public String getConnectionInitSql() { + return delegate.getConnectionInitSql(); } @Override - public void setLogAbandoned(boolean logAbandoned) { - delegate.setLogAbandoned(logAbandoned); + public void setConnectionInitSql(String connectionInitSql) { + delegate.setConnectionInitSql(connectionInitSql); } @Override - public void addConnectionProperty(String name, String value) { - delegate.addConnectionProperty(name, value); + public DataSource getDataSource() { + return delegate.getDataSource(); } @Override - public void removeConnectionProperty(String name) { - delegate.removeConnectionProperty(name); + public void setDataSource(DataSource dataSource) { + delegate.setDataSource(dataSource); } @Override - public void setConnectionProperties(String connectionProperties) { - delegate.setConnectionProperties(connectionProperties); + public String getDataSourceClassName() { + return delegate.getDataSourceClassName(); } @Override - public synchronized void close() throws SQLException { - delegate.close(); - } - - @Override - public synchronized boolean isClosed() { - return delegate.isClosed(); + public void setDataSourceClassName(String className) { + delegate.setDataSourceClassName(className); } @Override - public boolean isWrapperFor(Class<?> iface) throws SQLException { - return delegate.isWrapperFor(iface); + public void addDataSourceProperty(String propertyName, Object value) { + delegate.addDataSourceProperty(propertyName, value); } @Override - public <T> T unwrap(Class<T> iface) throws SQLException { - return delegate.unwrap(iface); + public String getDataSourceJNDI() { + return delegate.getDataSourceJNDI(); } @Override - public void setDefaultAutoCommit(Boolean defaultAutoCommit) { - delegate.setDefaultAutoCommit(defaultAutoCommit); + public void setDataSourceJNDI(String jndiDataSource) { + delegate.setDataSourceJNDI(jndiDataSource); } @Override - public void setDefaultReadOnly(Boolean defaultReadOnly) { - delegate.setDefaultReadOnly(defaultReadOnly); + public Properties getDataSourceProperties() { + return delegate.getDataSourceProperties(); } @Override - public Integer getDefaultQueryTimeout() { - return delegate.getDefaultQueryTimeout(); + public void setDataSourceProperties(Properties dsProperties) { + delegate.setDataSourceProperties(dsProperties); } @Override - public void setDefaultQueryTimeout(Integer defaultQueryTimeoutSeconds) { - delegate.setDefaultQueryTimeout(defaultQueryTimeoutSeconds); + public String getJdbcUrl() { + return delegate.getJdbcUrl(); } @Override - public String getDefaultSchema() { - return delegate.getDefaultSchema(); + public void setJdbcUrl(String jdbcUrl) { + delegate.setJdbcUrl(jdbcUrl); } @Override - public void setDefaultSchema(String defaultSchema) { - delegate.setDefaultSchema(defaultSchema); + public void setAutoCommit(boolean isAutoCommit) { + delegate.setAutoCommit(isAutoCommit); } @Override - public boolean getCacheState() { - return delegate.getCacheState(); + public boolean isAllowPoolSuspension() { + return delegate.isAllowPoolSuspension(); } @Override - public void setCacheState(boolean cacheState) { - delegate.setCacheState(cacheState); + public void setAllowPoolSuspension(boolean isAllowPoolSuspension) { + delegate.setAllowPoolSuspension(isAllowPoolSuspension); } @Override - public synchronized Driver getDriver() { - return delegate.getDriver(); + public long getInitializationFailTimeout() { + return delegate.getInitializationFailTimeout(); } @Override - public synchronized void setDriver(Driver driver) { - delegate.setDriver(driver); + public void setInitializationFailTimeout(long initializationFailTimeout) { + delegate.setInitializationFailTimeout(initializationFailTimeout); } @Override - public synchronized boolean getLifo() { - return delegate.getLifo(); + public boolean isIsolateInternalQueries() { + return delegate.isIsolateInternalQueries(); } @Override - public synchronized void setLifo(boolean lifo) { - delegate.setLifo(lifo); + public void setIsolateInternalQueries(boolean isolate) { + delegate.setIsolateInternalQueries(isolate); } @Override - public synchronized boolean getTestOnCreate() { - return delegate.getTestOnCreate(); + public MetricsTrackerFactory getMetricsTrackerFactory() { + return delegate.getMetricsTrackerFactory(); } @Override - public synchronized void setTestOnCreate(boolean testOnCreate) { - delegate.setTestOnCreate(testOnCreate); + public Object getMetricRegistry() { + return delegate.getMetricRegistry(); } @Override - public synchronized void setSoftMinEvictableIdleTimeMillis(long softMinEvictableIdleTimeMillis) { - delegate.setSoftMinEvictableIdleTimeMillis(softMinEvictableIdleTimeMillis); + public Object getHealthCheckRegistry() { + return delegate.getHealthCheckRegistry(); } @Override - public synchronized long getSoftMinEvictableIdleTimeMillis() { - return delegate.getSoftMinEvictableIdleTimeMillis(); + public Properties getHealthCheckProperties() { + return delegate.getHealthCheckProperties(); } @Override - public synchronized String getEvictionPolicyClassName() { - return delegate.getEvictionPolicyClassName(); + public void setHealthCheckProperties(Properties healthCheckProperties) { + delegate.setHealthCheckProperties(healthCheckProperties); } @Override - public synchronized void setEvictionPolicyClassName(String evictionPolicyClassName) { - delegate.setEvictionPolicyClassName(evictionPolicyClassName); + public void addHealthCheckProperty(String key, String value) { + delegate.addHealthCheckProperty(key, value); } @Override - public String[] getConnectionInitSqlsAsArray() { - return delegate.getConnectionInitSqlsAsArray(); + public long getKeepaliveTime() { + return delegate.getKeepaliveTime(); } @Override - public long getMaxConnLifetimeMillis() { - return delegate.getMaxConnLifetimeMillis(); + public void setKeepaliveTime(long keepaliveTimeMs) { + delegate.setKeepaliveTime(keepaliveTimeMs); } @Override - public boolean getLogExpiredConnections() { - return delegate.getLogExpiredConnections(); + public void setReadOnly(boolean readOnly) { + delegate.setReadOnly(readOnly); } @Override - public void setMaxConnLifetimeMillis(long maxConnLifetimeMillis) { - delegate.setMaxConnLifetimeMillis(maxConnLifetimeMillis); + public boolean isRegisterMbeans() { + return delegate.isRegisterMbeans(); } @Override - public void setLogExpiredConnections(boolean logExpiredConnections) { - delegate.setLogExpiredConnections(logExpiredConnections); + public void setRegisterMbeans(boolean register) { + delegate.setRegisterMbeans(register); } @Override - public String getJmxName() { - return delegate.getJmxName(); + public String getPoolName() { + return delegate.getPoolName(); } @Override - public void setJmxName(String jmxName) { - delegate.setJmxName(jmxName); + public void setPoolName(String poolName) { + delegate.setPoolName(poolName); } @Override - public boolean getEnableAutoCommitOnReturn() { - return delegate.getEnableAutoCommitOnReturn(); + public ScheduledExecutorService getScheduledExecutor() { + return delegate.getScheduledExecutor(); } @Override - public void setEnableAutoCommitOnReturn(boolean enableAutoCommitOnReturn) { - delegate.setEnableAutoCommitOnReturn(enableAutoCommitOnReturn); + public void setScheduledExecutor(ScheduledExecutorService executor) { + delegate.setScheduledExecutor(executor); } @Override - public boolean getRollbackOnReturn() { - return delegate.getRollbackOnReturn(); + public String getSchema() { + return delegate.getSchema(); } @Override - public void setRollbackOnReturn(boolean rollbackOnReturn) { - delegate.setRollbackOnReturn(rollbackOnReturn); + public void setSchema(String schema) { + delegate.setSchema(schema); } @Override - public Set<String> getDisconnectionSqlCodes() { - return delegate.getDisconnectionSqlCodes(); + public String getExceptionOverrideClassName() { + return delegate.getExceptionOverrideClassName(); } @Override - public String[] getDisconnectionSqlCodesAsArray() { - return delegate.getDisconnectionSqlCodesAsArray(); + public void setExceptionOverrideClassName(String exceptionOverrideClassName) { + delegate.setExceptionOverrideClassName(exceptionOverrideClassName); } @Override - public void setDisconnectionSqlCodes(Collection<String> disconnectionSqlCodes) { - delegate.setDisconnectionSqlCodes(disconnectionSqlCodes); + public ThreadFactory getThreadFactory() { + return delegate.getThreadFactory(); } @Override - public boolean getFastFailValidation() { - return delegate.getFastFailValidation(); + public void setThreadFactory(ThreadFactory threadFactory) { + delegate.setThreadFactory(threadFactory); } @Override - public void setFastFailValidation(boolean fastFailValidation) { - delegate.setFastFailValidation(fastFailValidation); + public void copyStateTo(HikariConfig other) { + delegate.copyStateTo(other); } @Override - public PrintWriter getAbandonedLogWriter() { - return delegate.getAbandonedLogWriter(); + public void validate() { + delegate.validate(); } @Override - public void setAbandonedLogWriter(PrintWriter logWriter) { - delegate.setAbandonedLogWriter(logWriter); + public ConnectionBuilder createConnectionBuilder() throws SQLException { + return delegate.createConnectionBuilder(); } @Override - public boolean getAbandonedUsageTracking() { - return delegate.getAbandonedUsageTracking(); + public ShardingKeyBuilder createShardingKeyBuilder() throws SQLException { + return delegate.createShardingKeyBuilder(); } - @Override - public void setAbandonedUsageTracking(boolean usageTracking) { - delegate.setAbandonedUsageTracking(usageTracking); - } - @Override - public void invalidateConnection(Connection connection) { - delegate.invalidateConnection(connection); - } - - @Override - public ObjectName preRegister(MBeanServer server, ObjectName objectName) { - return delegate.preRegister(server, objectName); - } - - @Override - public void postRegister(Boolean registrationDone) { - delegate.postRegister(registrationDone); - } - - @Override - public void preDeregister() throws Exception { - delegate.preDeregister(); - } - - @Override - public void postDeregister() { - delegate.postDeregister(); - } } diff --git a/server/sonar-db-core/src/test/java/org/sonar/db/DefaultDatabaseTest.java b/server/sonar-db-core/src/test/java/org/sonar/db/DefaultDatabaseTest.java index 67d05f4e1e8..07488e08e90 100644 --- a/server/sonar-db-core/src/test/java/org/sonar/db/DefaultDatabaseTest.java +++ b/server/sonar-db-core/src/test/java/org/sonar/db/DefaultDatabaseTest.java @@ -22,11 +22,13 @@ package org.sonar.db; import com.tngtech.java.junit.dataprovider.DataProvider; import com.tngtech.java.junit.dataprovider.DataProviderRunner; import com.tngtech.java.junit.dataprovider.UseDataProvider; +import com.zaxxer.hikari.HikariDataSource; import java.util.Properties; -import org.apache.commons.dbcp2.BasicDataSource; +import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; import org.sonar.api.config.internal.MapSettings; +import org.sonar.api.utils.log.LogTester; import org.sonar.db.dialect.PostgreSql; import org.sonar.process.logging.LogbackHelper; @@ -38,9 +40,11 @@ import static org.mockito.Mockito.mock; @RunWith(DataProviderRunner.class) public class DefaultDatabaseTest { - private LogbackHelper logbackHelper = mock(LogbackHelper.class); + private final LogbackHelper logbackHelper = mock(LogbackHelper.class); private static final String SONAR_JDBC = "sonar.jdbc."; + @Rule + public final LogTester logTester = new LogTester(); @Test public void shouldLoadDefaultValues() { @@ -54,19 +58,36 @@ public class DefaultDatabaseTest { } @Test - public void shouldExtractCommonsDbcpProperties() { + public void shouldExtractHikariProperties() { Properties props = new Properties(); props.setProperty("sonar.jdbc.driverClassName", "my.Driver"); props.setProperty("sonar.jdbc.username", "me"); - props.setProperty("sonar.jdbc.maxActive", "5"); - props.setProperty("sonar.jdbc.maxWait", "5000"); + props.setProperty("sonar.jdbc.maximumPoolSize", "5"); + props.setProperty("sonar.jdbc.connectionTimeout", "5000"); - Properties commonsDbcpProps = DefaultDatabase.extractCommonsDbcpProperties(props); + Properties hikariProps = DefaultDatabase.extractCommonsHikariProperties(props); - assertThat(commonsDbcpProps.getProperty("username")).isEqualTo("me"); - assertThat(commonsDbcpProps.getProperty("driverClassName")).isEqualTo("my.Driver"); - assertThat(commonsDbcpProps.getProperty("maxTotal")).isEqualTo("5"); - assertThat(commonsDbcpProps.getProperty("maxWaitMillis")).isEqualTo("5000"); + assertThat(hikariProps.getProperty("dataSource.user")).isEqualTo("me"); + assertThat(hikariProps.getProperty("driverClassName")).isEqualTo("my.Driver"); + assertThat(hikariProps.getProperty("maximumPoolSize")).isEqualTo("5"); + assertThat(hikariProps.getProperty("connectionTimeout")).isEqualTo("5000"); + } + + @Test + public void logWarningIfDeprecatedPropertyUsed() { + Properties props = new Properties(); + + props.setProperty("sonar.jdbc.maxIdle", "5"); + props.setProperty("sonar.jdbc.minEvictableIdleTimeMillis", "300000"); + props.setProperty("sonar.jdbc.timeBetweenEvictionRunsMillis", "1000"); + props.setProperty("sonar.jdbc.connectionTimeout", "8000"); + + DefaultDatabase.extractCommonsHikariProperties(props); + + assertThat(logTester.logs()) + .contains("Property [sonar.jdbc.maxIdle] has no effect as pool connection implementation changed, check 9.7 upgrade notes.") + .contains("Property [sonar.jdbc.minEvictableIdleTimeMillis] has no effect as pool connection implementation changed, check 9.7 upgrade notes.") + .contains("Property [sonar.jdbc.timeBetweenEvictionRunsMillis] has no effect as pool connection implementation changed, check 9.7 upgrade notes."); } @Test @@ -76,21 +97,21 @@ public class DefaultDatabaseTest { props.setProperty(jdbcProperty, "100"); props.setProperty(dbcpProperty, "100"); - Properties commonsDbcpProps = DefaultDatabase.extractCommonsDbcpProperties(props); + Properties commonsDbcpProps = DefaultDatabase.extractCommonsHikariProperties(props); assertThat(commonsDbcpProps.getProperty(removeStart(dbcpProperty, SONAR_JDBC))).isEqualTo("100"); } @Test @UseDataProvider("sonarJdbcAndDbcpProperties") - public void shouldThrowISEIfDuplicatedResolvedPropertiesWithDifferentValue(String jdbcProperty, String dbcpProperty) { + public void shouldThrowISEIfDuplicatedResolvedPropertiesWithDifferentValue(String jdbcProperty, String hikariProperty) { Properties props = new Properties(); props.setProperty(jdbcProperty, "100"); - props.setProperty(dbcpProperty, "200"); + props.setProperty(hikariProperty, "200"); - assertThatThrownBy(() -> DefaultDatabase.extractCommonsDbcpProperties(props)) + assertThatThrownBy(() -> DefaultDatabase.extractCommonsHikariProperties(props)) .isInstanceOf(IllegalStateException.class) - .hasMessageContaining(String.format("Duplicate property declaration for resolved jdbc key '%s': conflicting values are", removeStart(dbcpProperty, SONAR_JDBC))); + .hasMessageContaining(String.format("Duplicate property declaration for resolved jdbc key '%s': conflicting values are", removeStart(hikariProperty, SONAR_JDBC))); } @Test @@ -117,14 +138,14 @@ public class DefaultDatabaseTest { settings.setProperty("sonar.jdbc.driverClassName", "org.h2.Driver"); settings.setProperty("sonar.jdbc.username", "sonar"); settings.setProperty("sonar.jdbc.password", "sonar"); - settings.setProperty("sonar.jdbc.maxActive", "1"); + settings.setProperty("sonar.jdbc.maximumPoolSize", "1"); DefaultDatabase db = new DefaultDatabase(logbackHelper, settings); db.start(); db.stop(); assertThat(db.getDialect().getId()).isEqualTo("h2"); - assertThat(((BasicDataSource) db.getDataSource()).getMaxTotal()).isOne(); + assertThat(((HikariDataSource) db.getDataSource()).getMaximumPoolSize()).isOne(); } @Test @@ -152,8 +173,8 @@ public class DefaultDatabaseTest { @DataProvider public static Object[][] sonarJdbcAndDbcpProperties() { return new Object[][] { - {"sonar.jdbc.maxActive", "sonar.jdbc.maxTotal"}, - {"sonar.jdbc.maxWait", "sonar.jdbc.maxWaitMillis"} + {"sonar.jdbc.maxWait", "sonar.jdbc.connectionTimeout"}, + {"sonar.jdbc.maxActive", "sonar.jdbc.maximumPoolSize"} }; } } diff --git a/server/sonar-db-core/src/test/java/org/sonar/db/profiling/InvocationUtilsTest.java b/server/sonar-db-core/src/test/java/org/sonar/db/profiling/InvocationUtilsTest.java index 80f897169a1..4d657ace44c 100644 --- a/server/sonar-db-core/src/test/java/org/sonar/db/profiling/InvocationUtilsTest.java +++ b/server/sonar-db-core/src/test/java/org/sonar/db/profiling/InvocationUtilsTest.java @@ -23,6 +23,7 @@ import java.lang.reflect.Method; import java.sql.Connection; import java.sql.SQLException; import org.junit.Assert; +import org.junit.Ignore; import org.junit.Test; import org.sonar.test.TestUtils; @@ -52,16 +53,6 @@ public class InvocationUtilsTest { } @Test - public void should_wrap_undeclared_exception() throws Throwable { - Connection target = mock(Connection.class); - String failSql = "any sql"; - when(target.prepareStatement(failSql)).thenThrow(new SQLException("Expected")); - Method wait = Object.class.getMethod("wait"); - - Assert.assertThrows(IllegalStateException.class, () -> InvocationUtils.invokeQuietly(target, wait, new Object[0])); - } - - @Test public void only_static_methods() { assertThat(TestUtils.hasOnlyPrivateConstructors(InvocationUtils.class)).isTrue(); diff --git a/server/sonar-db-core/src/test/java/org/sonar/db/profiling/ProfiledDataSourceTest.java b/server/sonar-db-core/src/test/java/org/sonar/db/profiling/ProfiledDataSourceTest.java index cd1db27b42c..5a6a09a5d27 100644 --- a/server/sonar-db-core/src/test/java/org/sonar/db/profiling/ProfiledDataSourceTest.java +++ b/server/sonar-db-core/src/test/java/org/sonar/db/profiling/ProfiledDataSourceTest.java @@ -19,6 +19,8 @@ */ package org.sonar.db.profiling; +import com.zaxxer.hikari.HikariConfig; +import com.zaxxer.hikari.HikariDataSource; import java.io.ByteArrayInputStream; import java.lang.reflect.Method; import java.lang.reflect.Modifier; @@ -27,7 +29,9 @@ import java.sql.Date; import java.sql.PreparedStatement; import java.sql.Statement; import java.sql.Timestamp; -import org.apache.commons.dbcp2.BasicDataSource; +import java.util.Properties; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ThreadFactory; import org.junit.Rule; import org.junit.Test; import org.sonar.api.utils.log.LogTester; @@ -36,6 +40,7 @@ import org.sonar.api.utils.log.LoggerLevel; import static java.nio.charset.StandardCharsets.UTF_8; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; public class ProfiledDataSourceTest { @@ -43,7 +48,7 @@ public class ProfiledDataSourceTest { @Rule public LogTester logTester = new LogTester(); - BasicDataSource originDataSource = mock(BasicDataSource.class); + HikariDataSource originDataSource = mock(HikariDataSource.class); @Test public void execute_and_log_statement() throws Exception { @@ -59,7 +64,7 @@ public class ProfiledDataSourceTest { ProfiledDataSource underTest = new ProfiledDataSource(originDataSource, ProfiledConnectionInterceptor.INSTANCE); - assertThat(underTest.getUrl()).isNull(); + assertThat(underTest.getJdbcUrl()).isNull(); assertThat(underTest.getConnection().getClientInfo()).isNull(); final Statement statementProxy = underTest.getConnection().createStatement(); assertThat(statementProxy.getConnection()).isNull(); @@ -90,7 +95,7 @@ public class ProfiledDataSourceTest { ProfiledDataSource ds = new ProfiledDataSource(originDataSource, ProfiledConnectionInterceptor.INSTANCE); - assertThat(ds.getUrl()).isNull(); + assertThat(ds.getJdbcUrl()).isNull(); assertThat(ds.getConnection().getClientInfo()).isNull(); PreparedStatement preparedStatementProxy = ds.getConnection().prepareStatement(sqlWithParams); preparedStatementProxy.setInt(1, param1); @@ -121,7 +126,7 @@ public class ProfiledDataSourceTest { ProfiledDataSource ds = new ProfiledDataSource(originDataSource, ProfiledConnectionInterceptor.INSTANCE); - assertThat(ds.getUrl()).isNull(); + assertThat(ds.getJdbcUrl()).isNull(); assertThat(ds.getConnection().getClientInfo()).isNull(); PreparedStatement preparedStatementProxy = ds.getConnection().prepareStatement(sqlWithParams); assertThat(preparedStatementProxy.getConnection()).isNull(); @@ -144,7 +149,38 @@ public class ProfiledDataSourceTest { for (Method method : ProfiledDataSource.class.getDeclaredMethods()) { if (method.getParameterTypes().length == 0 && Modifier.isPublic(method.getModifiers())) { method.invoke(proxy); + } else if (method.getParameterTypes().length == 1 && method.getParameterTypes()[0].equals(String.class) && Modifier.isPublic(method.getModifiers())) { + method.invoke(proxy, "test"); + } else if (method.getParameterTypes().length == 1 && method.getParameterTypes()[0].equals(Boolean.TYPE) && Modifier.isPublic(method.getModifiers())) { + method.invoke(proxy, true); + } else if (method.getParameterTypes().length == 1 && method.getParameterTypes()[0].equals(Long.TYPE) && Modifier.isPublic(method.getModifiers())) { + method.invoke(proxy, 1L); + } else if (method.getParameterTypes().length == 1 && method.getParameterTypes()[0].equals(Integer.TYPE) && Modifier.isPublic(method.getModifiers())) { + method.invoke(proxy, 1); } } + + proxy.addHealthCheckProperty("test", "test"); + verify(originDataSource).addHealthCheckProperty("test", "test"); + + var schedulerMock = mock(ScheduledExecutorService.class); + proxy.setScheduledExecutor(schedulerMock); + verify(originDataSource).setScheduledExecutor(schedulerMock); + + var hikariConfigMock = mock(HikariConfig.class); + proxy.copyStateTo(hikariConfigMock); + verify(originDataSource).copyStateTo(hikariConfigMock); + + var threadFactoryMock = mock(ThreadFactory.class); + proxy.setThreadFactory(threadFactoryMock); + verify(originDataSource).setThreadFactory(threadFactoryMock); + + var properties = new Properties(); + proxy.setHealthCheckProperties(properties); + verify(originDataSource).setHealthCheckProperties(properties); + + proxy.setDataSourceProperties(properties); + verify(originDataSource).setDataSourceProperties(properties); + } } diff --git a/server/sonar-db-core/src/testFixtures/java/org/sonar/db/CoreH2Database.java b/server/sonar-db-core/src/testFixtures/java/org/sonar/db/CoreH2Database.java index 3a46a6b56e2..926b4e34583 100644 --- a/server/sonar-db-core/src/testFixtures/java/org/sonar/db/CoreH2Database.java +++ b/server/sonar-db-core/src/testFixtures/java/org/sonar/db/CoreH2Database.java @@ -19,11 +19,11 @@ */ package org.sonar.db; +import com.zaxxer.hikari.HikariDataSource; import java.io.PrintWriter; import java.sql.Connection; import java.sql.SQLException; import javax.sql.DataSource; -import org.apache.commons.dbcp2.BasicDataSource; import org.apache.commons.io.output.NullWriter; import org.apache.ibatis.io.Resources; import org.apache.ibatis.jdbc.ScriptRunner; @@ -38,7 +38,7 @@ import static java.lang.String.format; public class CoreH2Database implements Database { private static final String IGNORED_KEYWORDS_OPTION = ";NON_KEYWORDS=VALUE"; private final String name; - private BasicDataSource datasource; + private HikariDataSource datasource; /** * IMPORTANT: change DB name in order to not conflict with {@link DefaultDatabaseTest} @@ -54,11 +54,11 @@ public class CoreH2Database implements Database { private void startDatabase() { try { - datasource = new BasicDataSource(); + datasource = new HikariDataSource(); datasource.setDriverClassName("org.h2.Driver"); datasource.setUsername("sonar"); datasource.setPassword("sonar"); - datasource.setUrl("jdbc:h2:mem:" + name); + datasource.setJdbcUrl("jdbc:h2:mem:" + name); } catch (Exception e) { throw new IllegalStateException("Fail to start H2", e); } @@ -93,11 +93,7 @@ public class CoreH2Database implements Database { @Override public void stop() { - try { - datasource.close(); - } catch (SQLException e) { - // Ignore error - } + datasource.close(); } public DataSource getDataSource() { |