From c7c2da669803c8b57e9c294fa3ed1a33f1acc084 Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Thu, 12 Sep 2024 13:15:40 +0200 Subject: [PATCH 1/8] CB-5440. Init commit --- .../io.cloudbeaver.service.security/META-INF/MANIFEST.MF | 3 ++- .../src/io/cloudbeaver/service/security/db/CBDatabase.java | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF b/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF index 8a8a30cb1a..2ce180912a 100644 --- a/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF +++ b/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF @@ -14,7 +14,8 @@ Require-Bundle: org.jkiss.dbeaver.model;visibility:=reexport, org.jkiss.dbeaver.model.sql.jdbc, org.jkiss.dbeaver.registry;visibility:=reexport, org.jkiss.bundle.apache.dbcp;visibility:=reexport, - io.cloudbeaver.model + io.cloudbeaver.model, + org.jkiss.dbeaver.db.internal Export-Package: io.cloudbeaver.auth.provider.local, io.cloudbeaver.auth.provider.rp, io.cloudbeaver.service.security, diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 0c373781e4..54ac1e1ad5 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -67,7 +67,7 @@ /** * Database management */ -public class CBDatabase { +public class CBDatabase extends InternalDB { private static final Log log = Log.getLog(CBDatabase.class); public static final String SCHEMA_CREATE_SQL_PATH = "db/cb_schema_create.sql"; From 8f832ccbc1aef09d505bde1aa2adb65d28ef1bd6 Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Thu, 12 Sep 2024 17:49:49 +0200 Subject: [PATCH 2/8] CB-5440. Move logic to abstract class --- .../META-INF/MANIFEST.MF | 2 +- .../CBEmbeddedSecurityController.java | 2 +- .../EmbeddedSecurityControllerFactory.java | 2 +- .../service/security/db/CBDatabase.java | 56 +------------------ 4 files changed, 4 insertions(+), 58 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF b/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF index 2ce180912a..7cb0e99e03 100644 --- a/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF +++ b/server/bundles/io.cloudbeaver.service.security/META-INF/MANIFEST.MF @@ -15,7 +15,7 @@ Require-Bundle: org.jkiss.dbeaver.model;visibility:=reexport, org.jkiss.dbeaver.registry;visibility:=reexport, org.jkiss.bundle.apache.dbcp;visibility:=reexport, io.cloudbeaver.model, - org.jkiss.dbeaver.db.internal + org.jkiss.dbeaver.db.internal;visibility:=reexport Export-Package: io.cloudbeaver.auth.provider.local, io.cloudbeaver.auth.provider.rp, io.cloudbeaver.service.security, diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java index 7b21ede7fb..61ee710e42 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java @@ -3081,7 +3081,7 @@ private static void appendStringParameters(StringBuilder sql, @NotNull Collectio } public void shutdown() { - database.shutdown(); + database.closeConnection(); } public void finishConfiguration( diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java index 6c7b581b13..dcfc8f0eb1 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java @@ -81,7 +81,7 @@ application, database, new NoAuthCredentialsProvider(), smConfig try { database.initialize(); } catch (DBException e) { - database.shutdown(); + database.closeConnection(); throw e; } diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 54ac1e1ad5..2abad8e856 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -24,12 +24,11 @@ import io.cloudbeaver.registry.WebAuthProviderRegistry; import io.cloudbeaver.utils.WebAppUtils; import org.apache.commons.dbcp2.*; -import org.apache.commons.pool2.impl.GenericObjectPool; -import org.apache.commons.pool2.impl.GenericObjectPoolConfig; import org.jkiss.code.NotNull; import org.jkiss.code.Nullable; import org.jkiss.dbeaver.DBException; import org.jkiss.dbeaver.Log; +import org.jkiss.dbeaver.db.internal.InternalDB; import org.jkiss.dbeaver.model.DBConstants; import org.jkiss.dbeaver.model.auth.AuthInfo; import org.jkiss.dbeaver.model.connection.DBPDriver; @@ -237,27 +236,6 @@ public void initialize() throws DBException { log.debug("\tManagement database connection established"); } - protected PoolingDataSource initConnectionPool( - DBPDriver driver, - String dbURL, - Properties dbProperties, - Driver driverInstance - ) throws SQLException, DBException { - // Create connection pool with custom connection factory - log.debug("\tInitiate connection pool with management database (" + driver.getFullName() + "; " + dbURL + ")"); - DriverConnectionFactory conFactory = new DriverConnectionFactory(driverInstance, dbURL, dbProperties); - PoolableConnectionFactory pcf = new PoolableConnectionFactory(conFactory, null); - pcf.setValidationQuery(databaseConfiguration.getPool().getValidationQuery()); - - GenericObjectPoolConfig config = new GenericObjectPoolConfig<>(); - config.setMinIdle(databaseConfiguration.getPool().getMinIdleConnections()); - config.setMaxIdle(databaseConfiguration.getPool().getMaxIdleConnections()); - config.setMaxTotal(databaseConfiguration.getPool().getMaxConnections()); - GenericObjectPool connectionPool = new GenericObjectPool<>(pcf, config); - pcf.setPool(connectionPool); - return new PoolingDataSource<>(connectionPool); - } - //TODO move out public void finishConfiguration( @NotNull String adminName, @@ -351,17 +329,6 @@ private void grantAdminPermissionsToUser(String userId) throws DBException { userId); } - public void shutdown() { - log.debug("Shutdown database"); - if (cbDataSource != null) { - try { - cbDataSource.close(); - } catch (SQLException e) { - log.error(e); - } - } - } - private class CBSchemaVersionManager implements SQLSchemaVersionManager { @Override @@ -557,22 +524,6 @@ private void checkInstanceRecord(Connection connection) throws SQLException, IOE } } - private String getCurrentInstanceId() throws IOException { - // 16 chars - workspace ID - String workspaceId = DBWorkbench.getPlatform().getWorkspace().getWorkspaceId(); - if (workspaceId.length() > 16) { - workspaceId = workspaceId.substring(0, 16); - } - - StringBuilder id = new StringBuilder(36); - id.append("000000000000"); // there was mac address, but it generates dynamically when docker is used - id.append(":").append(workspaceId).append(":"); - while (id.length() < 36) { - id.append("X"); - } - return id.toString(); - } - /** * Replaces all predefined prefixes in sql query. */ @@ -581,11 +532,6 @@ public String normalizeTableNames(@NotNull String sql) { return CommonUtils.normalizeTableNames(sql, databaseConfiguration.getSchema()); } - @NotNull - public SQLDialect getDialect() { - return dialect; - } - public static boolean isDefaultH2Configuration(WebDatabaseConfig databaseConfiguration) { var workspace = WebAppUtils.getWebApplication().getWorkspaceDirectory(); var v1Path = workspace.resolve(".data").resolve(V1_DB_NAME); From 1793b9a701316ea2a381010356ea16ee4f97e81e Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Fri, 13 Sep 2024 15:18:39 +0200 Subject: [PATCH 3/8] CB-4095. Refactor after review, added sub group for envs --- .../service/security/db/CBDatabase.java | 59 ++++--------------- 1 file changed, 13 insertions(+), 46 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 2abad8e856..ecf1b2db75 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -45,12 +45,9 @@ import org.jkiss.dbeaver.model.sql.schema.ClassLoaderScriptSource; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaManager; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaVersionManager; -import org.jkiss.dbeaver.registry.DataSourceProviderRegistry; import org.jkiss.dbeaver.registry.storage.H2Migrator; -import org.jkiss.dbeaver.runtime.DBWorkbench; import org.jkiss.dbeaver.utils.GeneralUtils; import org.jkiss.dbeaver.utils.RuntimeUtils; -import org.jkiss.dbeaver.utils.SystemVariablesResolver; import org.jkiss.utils.CommonUtils; import org.jkiss.utils.IOUtils; import org.jkiss.utils.SecurityUtils; @@ -79,6 +76,7 @@ public class CBDatabase extends InternalDB { private static final String DEFAULT_DB_PWD_FILE = ".database-credentials.dat"; private static final String V1_DB_NAME = "cb.h2.dat"; private static final String V2_DB_NAME = "cb.h2v2.dat"; + public static final String CB_SCHEMA_INFO_TABLE_NAME = "CB_SCHEMA_INFO"; private final WebApplication application; private final WebDatabaseConfig databaseConfiguration; @@ -90,6 +88,7 @@ public class CBDatabase extends InternalDB { private SQLDialect dialect; public CBDatabase(WebApplication application, WebDatabaseConfig databaseConfiguration) { + super(databaseConfiguration, application); this.application = application; this.databaseConfiguration = databaseConfiguration; } @@ -118,11 +117,8 @@ public void initialize() throws DBException { if (CommonUtils.isEmpty(databaseConfiguration.getDriver())) { throw new DBException("No database driver configured for CloudBeaver database"); } - var dataSourceProviderRegistry = DataSourceProviderRegistry.getInstance(); - DBPDriver driver = dataSourceProviderRegistry.findDriver(databaseConfiguration.getDriver()); - if (driver == null) { - throw new DBException("Driver '" + databaseConfiguration.getDriver() + "' not found"); - } + var dataSourceProviderRegistry = getDataSourceProviderRegistry(); + DBPDriver driver = findDriver(dataSourceProviderRegistry); LoggingProgressMonitor monitor = new LoggingProgressMonitor(log); @@ -162,7 +158,7 @@ public void initialize() throws DBException { } } - String dbURL = GeneralUtils.replaceVariables(databaseConfiguration.getUrl(), SystemVariablesResolver.INSTANCE); + String dbURL = getDbURL(); Properties dbProperties = new Properties(); if (!CommonUtils.isEmpty(dbUser)) { dbProperties.put(DBConstants.DATA_SOURCE_PROPERTY_USER, dbUser); @@ -181,12 +177,12 @@ public void initialize() throws DBException { } // reload the driver and url due to a possible configuration update - driver = dataSourceProviderRegistry.findDriver(databaseConfiguration.getDriver()); + driver = findDriver(dataSourceProviderRegistry); if (driver == null) { throw new DBException("Driver '" + databaseConfiguration.getDriver() + "' not found"); } - Driver driverInstance = driver.getDriverInstance(monitor); - dbURL = GeneralUtils.replaceVariables(databaseConfiguration.getUrl(), SystemVariablesResolver.INSTANCE); + Driver driverInstance = getDriverInstance(driver, monitor); + dbURL = getDbURL(); try { this.cbDataSource = initConnectionPool(driver, dbURL, dbProperties, driverInstance); @@ -199,17 +195,8 @@ public void initialize() throws DBException { DatabaseMetaData metaData = connection.getMetaData(); log.debug("\tConnected to " + metaData.getDatabaseProductName() + " " + metaData.getDatabaseProductVersion()); - if (dialect instanceof SQLDialectSchemaController && CommonUtils.isNotEmpty(schemaName)) { - var dialectSchemaController = (SQLDialectSchemaController) dialect; - var schemaExistQuery = dialectSchemaController.getSchemaExistQuery(schemaName); - boolean schemaExist = JDBCUtils.executeQuery(connection, schemaExistQuery) != null; - if (!schemaExist) { - log.info("Schema " + schemaName + " not exist, create new one"); - String createSchemaQuery = dialectSchemaController.getCreateSchemaQuery( - schemaName - ); - JDBCUtils.executeStatement(connection, createSchemaQuery); - } + if (dialect instanceof SQLDialectSchemaController dialectSchemaController && CommonUtils.isNotEmpty(schemaName)) { + createSchemaIfNotExists(connection, dialectSchemaController, schemaName); } SQLSchemaManager schemaManager = new SQLSchemaManager( "CB", @@ -342,7 +329,7 @@ public int getCurrentSchemaVersion(DBRProgressMonitor monitor, Connection connec } catch (SQLException e) { try { Object legacyVersion = CommonUtils.toInt(JDBCUtils.executeQuery(connection, - normalizeTableNames("SELECT SCHEMA_VERSION FROM {table_prefix}CB_SERVER"))); + normalizeTableNames("SELECT SCHEMA_VERSION FROM {table_prefix}CB_SERVER"))); // may be remove? // Table CB_SERVER exist - this is a legacy schema return LEGACY_SCHEMA_VERSION; } catch (SQLException ex) { @@ -363,20 +350,8 @@ public void updateCurrentSchemaVersion( @NotNull Connection connection, @NotNull String schemaName, int version - ) throws DBException, SQLException { - var updateCount = JDBCUtils.executeUpdate( - connection, - normalizeTableNames("UPDATE {table_prefix}CB_SCHEMA_INFO SET VERSION=?,UPDATE_TIME=CURRENT_TIMESTAMP"), - version - ); - if (updateCount <= 0) { - JDBCUtils.executeSQL( - connection, - normalizeTableNames( - "INSERT INTO {table_prefix}CB_SCHEMA_INFO (VERSION,UPDATE_TIME) VALUES(?,CURRENT_TIMESTAMP)"), - version - ); - } + ) throws SQLException { + upsertSchemaInfo(connection, CB_SCHEMA_INFO_TABLE_NAME, schemaName, version); } @Override @@ -524,14 +499,6 @@ private void checkInstanceRecord(Connection connection) throws SQLException, IOE } } - /** - * Replaces all predefined prefixes in sql query. - */ - @NotNull - public String normalizeTableNames(@NotNull String sql) { - return CommonUtils.normalizeTableNames(sql, databaseConfiguration.getSchema()); - } - public static boolean isDefaultH2Configuration(WebDatabaseConfig databaseConfiguration) { var workspace = WebAppUtils.getWebApplication().getWorkspaceDirectory(); var v1Path = workspace.resolve(".data").resolve(V1_DB_NAME); From 27598cfb64d17cf4bd37f432069f6de32249a7af Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Fri, 13 Sep 2024 16:34:06 +0200 Subject: [PATCH 4/8] CB-4095. Fix build, add some refactoring, fix export package --- .../CBEmbeddedSecurityController.java | 2 +- .../EmbeddedSecurityControllerFactory.java | 2 +- .../service/security/db/CBDatabase.java | 23 +++++++++++++++---- 3 files changed, 20 insertions(+), 7 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java index 61ee710e42..7b21ede7fb 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java @@ -3081,7 +3081,7 @@ private static void appendStringParameters(StringBuilder sql, @NotNull Collectio } public void shutdown() { - database.closeConnection(); + database.shutdown(); } public void finishConfiguration( diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java index dcfc8f0eb1..6c7b581b13 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java @@ -81,7 +81,7 @@ application, database, new NoAuthCredentialsProvider(), smConfig try { database.initialize(); } catch (DBException e) { - database.closeConnection(); + database.shutdown(); throw e; } diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index ecf1b2db75..0815f0a605 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -319,13 +319,10 @@ private void grantAdminPermissionsToUser(String userId) throws DBException { private class CBSchemaVersionManager implements SQLSchemaVersionManager { @Override - public int getCurrentSchemaVersion(DBRProgressMonitor monitor, Connection connection, String schemaName) - throws DBException, SQLException { + public int getCurrentSchemaVersion(DBRProgressMonitor monitor, Connection connection, String schemaName) { // Check and update schema try { - int version = CommonUtils.toInt(JDBCUtils.executeQuery(connection, - normalizeTableNames("SELECT VERSION FROM {table_prefix}CB_SCHEMA_INFO"))); - return version == 0 ? 1 : version; + return getVersionFromSchema(connection, "CB_SCHEMA_INFO", null); } catch (SQLException e) { try { Object legacyVersion = CommonUtils.toInt(JDBCUtils.executeQuery(connection, @@ -520,4 +517,20 @@ protected WebApplication getApplication() { protected SMAdminController getAdminSecurityController() { return adminSecurityController; } + + @NotNull + public SQLDialect getDialect() { + return dialect; + } + + public void shutdown() { + log.debug("Shutdown database"); + if (cbDataSource != null) { + try { + cbDataSource.close(); + } catch (SQLException e) { + log.error(e); + } + } + } } From 19dd5742133f0044d7abb56d140bef9c8b5c1495 Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Thu, 19 Sep 2024 13:09:03 +0200 Subject: [PATCH 5/8] CB-5440. Refactor after review --- .../service/security/db/CBDatabase.java | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 0815f0a605..c9c119fb7f 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -46,6 +46,7 @@ import org.jkiss.dbeaver.model.sql.schema.SQLSchemaManager; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaVersionManager; import org.jkiss.dbeaver.registry.storage.H2Migrator; +import org.jkiss.dbeaver.runtime.DBWorkbench; import org.jkiss.dbeaver.utils.GeneralUtils; import org.jkiss.dbeaver.utils.RuntimeUtils; import org.jkiss.utils.CommonUtils; @@ -326,7 +327,7 @@ public int getCurrentSchemaVersion(DBRProgressMonitor monitor, Connection connec } catch (SQLException e) { try { Object legacyVersion = CommonUtils.toInt(JDBCUtils.executeQuery(connection, - normalizeTableNames("SELECT SCHEMA_VERSION FROM {table_prefix}CB_SERVER"))); // may be remove? + normalizeTableNames("SELECT SCHEMA_VERSION FROM {table_prefix}CB_SERVER"))); // Table CB_SERVER exist - this is a legacy schema return LEGACY_SCHEMA_VERSION; } catch (SQLException ex) { @@ -533,4 +534,20 @@ public void shutdown() { } } } + + protected String getCurrentInstanceId() throws IOException { + // 16 chars - workspace ID + String workspaceId = DBWorkbench.getPlatform().getWorkspace().getWorkspaceId(); + if (workspaceId.length() > 16) { + workspaceId = workspaceId.substring(0, 16); + } + + StringBuilder id = new StringBuilder(36); + id.append("000000000000"); // there was mac address, but it generates dynamically when docker is used + id.append(":").append(workspaceId).append(":"); + while (id.length() < 36) { + id.append("X"); + } + return id.toString(); + } } From 3fcaf75e8b58d48903eb824164b49340b48dc958 Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Thu, 19 Sep 2024 13:40:16 +0200 Subject: [PATCH 6/8] CB-5440. Move more logic to InternalDB --- .../service/security/db/CBDatabase.java | 52 +++++-------------- 1 file changed, 13 insertions(+), 39 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index c9c119fb7f..507543ccd2 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -40,22 +40,17 @@ import org.jkiss.dbeaver.model.security.SMAdminController; import org.jkiss.dbeaver.model.security.user.SMTeam; import org.jkiss.dbeaver.model.security.user.SMUser; -import org.jkiss.dbeaver.model.sql.SQLDialect; -import org.jkiss.dbeaver.model.sql.SQLDialectSchemaController; import org.jkiss.dbeaver.model.sql.schema.ClassLoaderScriptSource; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaManager; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaVersionManager; import org.jkiss.dbeaver.registry.storage.H2Migrator; import org.jkiss.dbeaver.runtime.DBWorkbench; import org.jkiss.dbeaver.utils.GeneralUtils; -import org.jkiss.dbeaver.utils.RuntimeUtils; import org.jkiss.utils.CommonUtils; import org.jkiss.utils.IOUtils; import org.jkiss.utils.SecurityUtils; import java.io.*; -import java.net.InetAddress; -import java.net.UnknownHostException; import java.nio.charset.StandardCharsets; import java.sql.*; import java.util.*; @@ -78,15 +73,15 @@ public class CBDatabase extends InternalDB { private static final String V1_DB_NAME = "cb.h2.dat"; private static final String V2_DB_NAME = "cb.h2v2.dat"; public static final String CB_SCHEMA_INFO_TABLE_NAME = "CB_SCHEMA_INFO"; + public static final String MAC_ADDRESS = "macAddress"; + public static final String HOST_NAME = "hostName"; private final WebApplication application; private final WebDatabaseConfig databaseConfiguration; - private PoolingDataSource cbDataSource; private transient volatile Connection exclusiveConnection; private String instanceId; private SMAdminController adminSecurityController; - private SQLDialect dialect; public CBDatabase(WebApplication application, WebDatabaseConfig databaseConfiguration) { super(databaseConfiguration, application); @@ -106,11 +101,7 @@ public Connection openConnection() throws SQLException { if (exclusiveConnection != null) { return exclusiveConnection; } - return cbDataSource.getConnection(); - } - - public PoolingDataSource getConnectionPool() { - return cbDataSource; + return getDbConnection().getConnection(); } public void initialize() throws DBException { @@ -186,19 +177,16 @@ public void initialize() throws DBException { dbURL = getDbURL(); try { - this.cbDataSource = initConnectionPool(driver, dbURL, dbProperties, driverInstance); + super.setDbConnection(initConnectionPool(driver, dbURL, dbProperties, driverInstance)); } catch (SQLException e) { throw new DBException("Error initializing connection pool"); } - dialect = driver.getScriptDialect().createInstance(); - try (Connection connection = cbDataSource.getConnection()) { + try (Connection connection = getDbConnection().getConnection()) { DatabaseMetaData metaData = connection.getMetaData(); log.debug("\tConnected to " + metaData.getDatabaseProductName() + " " + metaData.getDatabaseProductVersion()); - if (dialect instanceof SQLDialectSchemaController dialectSchemaController && CommonUtils.isNotEmpty(schemaName)) { - createSchemaIfNotExists(connection, dialectSchemaController, schemaName); - } + createSchema(driver, schemaName, connection); SQLSchemaManager schemaManager = new SQLSchemaManager( "CB", new ClassLoaderScriptSource( @@ -208,7 +196,7 @@ public void initialize() throws DBException { ), monitor1 -> connection, new CBSchemaVersionManager(), - dialect, + getDialect(), null, schemaName, CURRENT_SCHEMA_VERSION, @@ -432,15 +420,7 @@ protected void validateInstancePersistentState(Connection connection) throws IOE } private void checkInstanceRecord(Connection connection) throws SQLException, IOException { - String hostName; - try { - hostName = InetAddress.getLocalHost().getHostName(); - } catch (UnknownHostException e) { - hostName = "localhost"; - } - - byte[] hardwareAddress = RuntimeUtils.getLocalMacAddress(); - String macAddress = CommonUtils.toHexString(hardwareAddress); + Map hostInfo = getHostInfo(); instanceId = getCurrentInstanceId(); @@ -457,8 +437,8 @@ private void checkInstanceRecord(Connection connection) throws SQLException, IOE "(INSTANCE_ID,MAC_ADDRESS,HOST_NAME,PRODUCT_NAME,PRODUCT_VERSION,UPDATE_TIME)" + " VALUES(?,?,?,?,?,CURRENT_TIMESTAMP)"), instanceId, - macAddress, - hostName, + hostInfo.get(MAC_ADDRESS), + hostInfo.get(HOST_NAME), productName, versionName); } else { @@ -467,7 +447,7 @@ private void checkInstanceRecord(Connection connection) throws SQLException, IOE normalizeTableNames("UPDATE {table_prefix}CB_INSTANCE " + "SET HOST_NAME=?,PRODUCT_NAME=?,PRODUCT_VERSION=?,UPDATE_TIME=CURRENT_TIMESTAMP " + "WHERE INSTANCE_ID=?"), - hostName, + hostInfo.get(HOST_NAME), productName, versionName, instanceId); @@ -518,17 +498,11 @@ protected WebApplication getApplication() { protected SMAdminController getAdminSecurityController() { return adminSecurityController; } - - @NotNull - public SQLDialect getDialect() { - return dialect; - } - public void shutdown() { log.debug("Shutdown database"); - if (cbDataSource != null) { + if (getDbConnection() != null) { try { - cbDataSource.close(); + getDbConnection().close(); } catch (SQLException e) { log.error(e); } From b1301d9d47a6eb824b3e5f5a9215f644cec8dbfa Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Thu, 19 Sep 2024 15:20:54 +0200 Subject: [PATCH 7/8] CB-5440. Move more logic to InternalDB --- .../CBEmbeddedSecurityController.java | 2 +- .../EmbeddedSecurityControllerFactory.java | 2 +- .../service/security/db/CBDatabase.java | 24 ++++++------------- 3 files changed, 9 insertions(+), 19 deletions(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java index 7b21ede7fb..61ee710e42 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/CBEmbeddedSecurityController.java @@ -3081,7 +3081,7 @@ private static void appendStringParameters(StringBuilder sql, @NotNull Collectio } public void shutdown() { - database.shutdown(); + database.closeConnection(); } public void finishConfiguration( diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java index 6c7b581b13..dcfc8f0eb1 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/EmbeddedSecurityControllerFactory.java @@ -81,7 +81,7 @@ application, database, new NoAuthCredentialsProvider(), smConfig try { database.initialize(); } catch (DBException e) { - database.shutdown(); + database.closeConnection(); throw e; } diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 507543ccd2..ba3e4eb4e0 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -41,7 +41,6 @@ import org.jkiss.dbeaver.model.security.user.SMTeam; import org.jkiss.dbeaver.model.security.user.SMUser; import org.jkiss.dbeaver.model.sql.schema.ClassLoaderScriptSource; -import org.jkiss.dbeaver.model.sql.schema.SQLSchemaManager; import org.jkiss.dbeaver.model.sql.schema.SQLSchemaVersionManager; import org.jkiss.dbeaver.registry.storage.H2Migrator; import org.jkiss.dbeaver.runtime.DBWorkbench; @@ -73,8 +72,8 @@ public class CBDatabase extends InternalDB { private static final String V1_DB_NAME = "cb.h2.dat"; private static final String V2_DB_NAME = "cb.h2v2.dat"; public static final String CB_SCHEMA_INFO_TABLE_NAME = "CB_SCHEMA_INFO"; - public static final String MAC_ADDRESS = "macAddress"; - public static final String HOST_NAME = "hostName"; + private static final String MAC_ADDRESS = "macAddress"; + private static final String HOST_NAME = "hostName"; private final WebApplication application; private final WebDatabaseConfig databaseConfiguration; @@ -187,7 +186,8 @@ public void initialize() throws DBException { log.debug("\tConnected to " + metaData.getDatabaseProductName() + " " + metaData.getDatabaseProductVersion()); createSchema(driver, schemaName, connection); - SQLSchemaManager schemaManager = new SQLSchemaManager( + + updateSchema( "CB", new ClassLoaderScriptSource( CBDatabase.class.getClassLoader(), @@ -201,9 +201,9 @@ public void initialize() throws DBException { schemaName, CURRENT_SCHEMA_VERSION, 0, - databaseConfiguration + databaseConfiguration, + monitor ); - schemaManager.updateSchema(monitor); validateInstancePersistentState(connection); } catch (Exception e) { @@ -498,18 +498,8 @@ protected WebApplication getApplication() { protected SMAdminController getAdminSecurityController() { return adminSecurityController; } - public void shutdown() { - log.debug("Shutdown database"); - if (getDbConnection() != null) { - try { - getDbConnection().close(); - } catch (SQLException e) { - log.error(e); - } - } - } - protected String getCurrentInstanceId() throws IOException { + protected String getCurrentInstanceId() { // 16 chars - workspace ID String workspaceId = DBWorkbench.getPlatform().getWorkspace().getWorkspaceId(); if (workspaceId.length() > 16) { From 7af78a95d019f24fd96eefbc4089fdb25fd4144a Mon Sep 17 00:00:00 2001 From: "denis.sinelnikov" Date: Tue, 10 Dec 2024 12:57:41 +0100 Subject: [PATCH 8/8] CB-5440. Fixed update schema if schema exist --- .../src/io/cloudbeaver/service/security/db/CBDatabase.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java index 484d06dc40..7b3af323ff 100644 --- a/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java +++ b/server/bundles/io.cloudbeaver.service.security/src/io/cloudbeaver/service/security/db/CBDatabase.java @@ -315,7 +315,7 @@ private class CBSchemaVersionManager implements SQLSchemaVersionManager { public int getCurrentSchemaVersion(DBRProgressMonitor monitor, Connection connection, String schemaName) { // Check and update schema try { - return getVersionFromSchema(connection, "CB_SCHEMA_INFO", null); + return getVersionFromSchema(connection, "CB_SCHEMA_INFO", schemaName); } catch (SQLException e) { try { Object legacyVersion = CommonUtils.toInt(JDBCUtils.executeQuery(connection,