Skip to content

Commit

Permalink
fix: Invalid database connection is saved AND used despite "CANCEL"
Browse files Browse the repository at this point in the history
(cherry picked from commit cd6555e)
  • Loading branch information
befc authored and smmribeiro committed Dec 9, 2024
1 parent 180052b commit 74aead5
Show file tree
Hide file tree
Showing 3 changed files with 56 additions and 27 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,11 @@ public class PooledDatasourceHelper {

public static PoolingDataSource setupPooledDataSource( IDatabaseConnection databaseConnection )
throws DBDatasourceServiceException {
return setupPooledDataSource( databaseConnection, true );
}

public static PoolingDataSource setupPooledDataSource( IDatabaseConnection databaseConnection, boolean useCache )
throws DBDatasourceServiceException {
try {
if ( databaseConnection.getAccessType().equals( DatabaseAccessType.JNDI ) ) {
throwDBDatasourceServiceException( databaseConnection.getName(), "PooledDatasourceHelper.ERROR_0008_UNABLE_TO_POOL_DATASOURCE_IT_IS_JNDI" );
Expand All @@ -66,9 +70,10 @@ public static PoolingDataSource setupPooledDataSource( IDatabaseConnection datab
loadDriverClass( databaseConnection, dialect, driverClass );

PoolingManagedDataSource poolingDataSource = new PoolingManagedDataSource( databaseConnection, dialect );

ICacheManager cacheManager = PentahoSystem.getCacheManager( null );
cacheManager.putInRegionCache( IDBDatasourceService.JDBC_DATASOURCE, databaseConnection.getName(), poolingDataSource );
if ( useCache ) {
ICacheManager cacheManager = PentahoSystem.getCacheManager( null );
cacheManager.putInRegionCache( IDBDatasourceService.JDBC_DATASOURCE, databaseConnection.getName(), poolingDataSource );
}
return poolingDataSource;
} catch ( Exception e ) {
throw new DBDatasourceServiceException( e );
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -223,6 +223,46 @@ protected void initWithJNDI( final String jndiName ) {
}
}

private void initOther( Properties props ) {
String connectionName = props.getProperty( IPentahoConnection.CONNECTION_NAME );
if ( connectionName != null && !connectionName.isEmpty() ) {
boolean isTestConnection = isTestConnection( connectionName );
if ( isTestConnection ) {
handleTestConnection( props, connectionName );
}
IDatabaseConnection databaseConnection = (IDatabaseConnection) props.get( IPentahoConnection.CONNECTION );
// If the connection is a test connection, we don't want to cache it
initDataSource( databaseConnection, !isTestConnection );
} else {
String driver = props.getProperty( IPentahoConnection.DRIVER_KEY );
String provider = props.getProperty( IPentahoConnection.LOCATION_KEY );
String userName = props.getProperty( IPentahoConnection.USERNAME_KEY );
String password = props.getProperty( IPentahoConnection.PASSWORD_KEY );
init( driver, provider, userName, password );
String query = props.getProperty( IPentahoConnection.QUERY_KEY );
if ( query != null && !query.isEmpty() ) {
try {
executeQuery( query );
} catch ( Exception e ) {
logger.error( "Can't execute query", e );
}
}
}
}

private static boolean isTestConnection( String connectionName ) {
return connectionName.length() > 16
&& connectionName.startsWith( "__TEST__" )
&& connectionName.endsWith( "__TEST__" );
}

private static void handleTestConnection( Properties props, String connectionName ) {
connectionName = connectionName.substring( 8, connectionName.length() - 8 );
props.setProperty( IPentahoConnection.CONNECTION_NAME, connectionName );
}



/**
* Allows the native SQL Connection to be enhanced in a subclass. Best used when a connection needs to be enhanced
* with an "effective user"
Expand Down Expand Up @@ -283,7 +323,9 @@ private void closeStatements() {
* iterate over and close all resultsets. Remove each result set from the list.
*/
private void closeResultSets() {
Iterator iter = resultSets.iterator();
private static boolean isTestConnection( String connectionName ) {
return connectionName.length() > 12 && connectionName.startsWith( "__TEST__" ) && connectionName.endsWith( "__TEST__" );
} Iterator iter = resultSets.iterator();
while ( iter.hasNext() ) {
IPentahoResultSet rset = (IPentahoResultSet) iter.next();
if ( rset != null ) {
Expand Down Expand Up @@ -571,9 +613,9 @@ public IPentahoResultSet getResultSet() {
return sqlResultSet;
}

void initDataSource( IDatabaseConnection databaseConnection ) {
void initDataSource( IDatabaseConnection databaseConnection, boolean useCache ) {
try {
DataSource dataSource = PooledDatasourceHelper.setupPooledDataSource( databaseConnection );
DataSource dataSource = PooledDatasourceHelper.setupPooledDataSource( databaseConnection, useCache );
nativeConnection = captureConnection( dataSource.getConnection() );
} catch ( Exception e ) {
logger.error( "Can't get connection from Pool", e );
Expand All @@ -586,25 +628,7 @@ public boolean connect( final Properties props ) {
if ( jndiName != null && !jndiName.isEmpty() ) {
initWithJNDI( jndiName );
} else {
String connectionName = props.getProperty( IPentahoConnection.CONNECTION_NAME );
if ( connectionName != null && !connectionName.isEmpty() ) {
IDatabaseConnection databaseConnection = (IDatabaseConnection) props.get( IPentahoConnection.CONNECTION );
initDataSource( databaseConnection );
} else {
String driver = props.getProperty( IPentahoConnection.DRIVER_KEY );
String provider = props.getProperty( IPentahoConnection.LOCATION_KEY );
String userName = props.getProperty( IPentahoConnection.USERNAME_KEY );
String password = props.getProperty( IPentahoConnection.PASSWORD_KEY );
init( driver, provider, userName, password );
String query = props.getProperty( IPentahoConnection.QUERY_KEY );
if ( query != null && !query.isEmpty() ) {
try {
executeQuery( query );
} catch ( Exception e ) {
logger.error( "Can't execute query", e );
}
}
}
initOther( props );
}
return ( nativeConnection != null && !isClosed() );
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ public boolean matches( final Class<?> arg ) {
@Test
public void testConnect() {
SQLConnection sqlc = spy( new SQLConnection() );
Properties props = new Properties();
Properties props;

props = new Properties();
props.put( IPentahoConnection.JNDI_NAME_KEY, "test" );
Expand All @@ -94,7 +94,7 @@ public void testConnect() {
doNothing().when( sqlc ).init( nullable( String.class ), nullable( String.class ), nullable( String.class ), nullable( String.class ) );
assertTrue( "NonPool Test", sqlc.connect( props ) );

doNothing().when( sqlc ).initDataSource( nullable( IDatabaseConnection.class ) );
doNothing().when( sqlc ).initDataSource( nullable( IDatabaseConnection.class ), true );

props.put( IPentahoConnection.CONNECTION_NAME, "test" );
assertTrue( "Pool Test", sqlc.connect( props ) );
Expand Down

0 comments on commit 74aead5

Please sign in to comment.