From 5b0a3607f655b5d4756987dfbf9baaa678ef8c37 Mon Sep 17 00:00:00 2001 From: Rob Bygrave Date: Mon, 6 Nov 2023 12:14:27 +1300 Subject: [PATCH 1/2] Fix to return DataSourceBuilder.Settings for getDataSourceConfig() and getReadOnlyDataSourceConfig() That is, existing code using DataSourceConfig has access to the getter methods of DataSourceConfig. The DataSourceBuilder interface only has the setter methods and DataSourceBuilder.Settings has both getters and setter methods. That is, the refactor to extract the DataSourceBuilder interface also split off the getter methods to the DataSourceBuilder.Settings interface (because most of the time when using the builder we only need the setter methods and effectively hiding the getter methods behind the settings() is useful to simplify the API for users). --- .../main/java/io/ebean/DatabaseBuilder.java | 27 +++++++++++++++++-- .../java/io/ebean/config/DatabaseConfig.java | 23 ++++++++++------ .../server/core/DatabasePlatformFactory.java | 2 +- .../server/core/DefaultContainer.java | 2 +- .../server/core/InitDataSource.java | 18 ++++++------- .../server/core/InitDataSourceTest.java | 2 +- .../test/config/AutoConfigureForTesting.java | 4 +-- 7 files changed, 53 insertions(+), 25 deletions(-) diff --git a/ebean-api/src/main/java/io/ebean/DatabaseBuilder.java b/ebean-api/src/main/java/io/ebean/DatabaseBuilder.java index f3350d858..a9a856bed 100644 --- a/ebean-api/src/main/java/io/ebean/DatabaseBuilder.java +++ b/ebean-api/src/main/java/io/ebean/DatabaseBuilder.java @@ -20,10 +20,16 @@ import jakarta.persistence.EnumType; import javax.sql.DataSource; import java.time.Clock; import java.util.*; +import java.util.function.BooleanSupplier; +import java.util.function.Consumer; import java.util.function.Function; /** * Build a Database instance. + *

+ * Note that {@link #settings()} provides access to read the builder configuration + * (the getters). The DatabaseBuilder only has the methods to set builder configuration + * (the setters) so use {@link #settings()} to access to everything. * *

{@code
  *
@@ -64,6 +70,23 @@ public interface DatabaseBuilder {
    */
   Settings settings();
 
+  /**
+   * Apply configuration to this builder using a lambda.
+   */
+  DatabaseBuilder apply(Consumer applyConfiguration);
+
+  /**
+   * Conditionally apply configuration to this builder via a lambda.
+   *
+   * @param predicate The condition to apply configuration when true.
+   * @param apply     The configuration to apply to this builder.
+   */
+  default DatabaseBuilder alsoIf(BooleanSupplier predicate, Consumer apply) {
+    if (predicate.getAsBoolean()) {
+      apply(apply);
+    }
+    return this;
+  }
   /**
    * Set the name of the Database.
    */
@@ -2598,7 +2621,7 @@ public interface DatabaseBuilder {
      * Return the configuration to build a DataSource using Ebean's own DataSource
      * implementation.
      */
-    DataSourceBuilder getDataSourceConfig();
+    DataSourceBuilder.Settings getDataSourceConfig();
 
     /**
      * Return true if Ebean should create a DataSource for use with implicit read only transactions.
@@ -2614,7 +2637,7 @@ public interface DatabaseBuilder {
      * set on this configuration. This means there is actually no need to set any configuration here and we only
      * set configuration for url, username and password etc if it is different from the main DataSource.
      */
-    DataSourceBuilder getReadOnlyDataSourceConfig();
+    DataSourceBuilder.Settings getReadOnlyDataSourceConfig();
 
     /**
      * Return a value used to represent TRUE in the database.
diff --git a/ebean-api/src/main/java/io/ebean/config/DatabaseConfig.java b/ebean-api/src/main/java/io/ebean/config/DatabaseConfig.java
index f7c633681..30d72e55e 100644
--- a/ebean-api/src/main/java/io/ebean/config/DatabaseConfig.java
+++ b/ebean-api/src/main/java/io/ebean/config/DatabaseConfig.java
@@ -27,6 +27,7 @@ import java.time.Clock;
 import java.time.ZonedDateTime;
 import java.time.format.DateTimeFormatter;
 import java.util.*;
+import java.util.function.Consumer;
 import java.util.function.Function;
 
 /**
@@ -316,7 +317,7 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
   /**
    * The data source config.
    */
-  private DataSourceBuilder dataSourceConfig = DataSourceBuilder.create();
+  private DataSourceBuilder.Settings dataSourceConfig = DataSourceBuilder.create().settings();
 
   /**
    * When true create a read only DataSource using readOnlyDataSourceConfig defaulting values from dataSourceConfig.
@@ -329,7 +330,7 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
   /**
    * Optional configuration for a read only data source.
    */
-  private DataSourceBuilder readOnlyDataSourceConfig = DataSourceBuilder.create();
+  private DataSourceBuilder.Settings readOnlyDataSourceConfig = DataSourceBuilder.create().settings();
 
   /**
    * Optional - the database schema that should be used to own the tables etc.
@@ -560,6 +561,12 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
     return this;
   }
 
+  @Override
+  public DatabaseBuilder apply(Consumer applyConfiguration) {
+    applyConfiguration.accept(this);
+    return this;
+  }
+
   @Override
   public Clock getClock() {
     return clock;
@@ -1359,13 +1366,13 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
   }
 
   @Override
-  public DataSourceBuilder getDataSourceConfig() {
+  public DataSourceBuilder.Settings getDataSourceConfig() {
     return dataSourceConfig;
   }
 
   @Override
   public DatabaseConfig setDataSourceConfig(DataSourceBuilder dataSourceConfig) {
-    this.dataSourceConfig = dataSourceConfig;
+    this.dataSourceConfig = dataSourceConfig.settings();
     return this;
   }
 
@@ -1381,13 +1388,13 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
   }
 
   @Override
-  public DataSourceBuilder getReadOnlyDataSourceConfig() {
+  public DataSourceBuilder.Settings getReadOnlyDataSourceConfig() {
     return readOnlyDataSourceConfig;
   }
 
   @Override
-  public DatabaseConfig setReadOnlyDataSourceConfig(DataSourceBuilder readOnlyDataSourceConfig) {
-    this.readOnlyDataSourceConfig = readOnlyDataSourceConfig;
+  public DatabaseConfig setReadOnlyDataSourceConfig(DataSourceBuilder readOnly) {
+    this.readOnlyDataSourceConfig = readOnly == null ? null : readOnly.settings();
     return this;
   }
 
@@ -2098,7 +2105,7 @@ public class DatabaseConfig implements DatabaseBuilder.Settings {
     loadAutoTuneSettings(p);
 
     if (dataSourceConfig == null) {
-      dataSourceConfig = DataSourceBuilder.create();
+      dataSourceConfig = DataSourceBuilder.create().settings();
     }
     loadDataSourceSettings(p);
 
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/DatabasePlatformFactory.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/DatabasePlatformFactory.java
index 20a693e6e..d0b0d1775 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/DatabasePlatformFactory.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/DatabasePlatformFactory.java
@@ -48,7 +48,7 @@ public class DatabasePlatformFactory {
         // choose based on dbName
         return byDatabaseName(config.getDatabasePlatformName());
       }
-      if (config.getDataSourceConfig().settings().isOffline()) {
+      if (config.getDataSourceConfig().isOffline()) {
         throw new PersistenceException("DatabasePlatformName must be specified with offline mode");
       }
       // guess using meta data from driver
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/DefaultContainer.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/DefaultContainer.java
index 70cb3ce52..30817020a 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/DefaultContainer.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/DefaultContainer.java
@@ -243,7 +243,7 @@ public final class DefaultContainer implements SpiContainer {
       return false;
     }
     if (config.getDataSource() == null) {
-      if (config.getDataSourceConfig().settings().isOffline()) {
+      if (config.getDataSourceConfig().isOffline()) {
         // this is ok - offline DDL generation etc
         return false;
       }
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/InitDataSource.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/InitDataSource.java
index b40b740e9..c5fead0da 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/InitDataSource.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/InitDataSource.java
@@ -49,18 +49,17 @@ final class InitDataSource {
     return roConfig == null ? null : createFromConfig(roConfig, true);
   }
 
-  DataSourceBuilder readOnlyConfig() {
+  DataSourceBuilder.Settings readOnlyConfig() {
     var roConfig = config.getReadOnlyDataSourceConfig();
     if (roConfig == null) {
       // it has explicitly been set to null, not expected but ok
       return null;
     }
-    var roSettings = roConfig.settings();
-    if (urlSet(roSettings.getUrl())) {
+    if (urlSet(roConfig.getUrl())) {
       return roConfig;
     }
     // convenient alternate place to set the read-only url
-    final String readOnlyUrl = config.getDataSourceConfig().settings().getReadOnlyUrl();
+    final String readOnlyUrl = config.getDataSourceConfig().getReadOnlyUrl();
     if (urlSet(readOnlyUrl)) {
       roConfig.url(readOnlyUrl);
       return roConfig;
@@ -77,23 +76,22 @@ final class InitDataSource {
     return url != null && !"none".equalsIgnoreCase(url) && !url.trim().isEmpty();
   }
 
-  private DataSource createFromConfig(DataSourceBuilder dsConfig, boolean readOnly) {
+  private DataSource createFromConfig(DataSourceBuilder.Settings dsConfig, boolean readOnly) {
     if (dsConfig == null) {
       throw new PersistenceException("No  DataSourceBuilder defined for " + config.getName());
     }
-    var dsSettings = dsConfig.settings();
-    if (dsSettings.isOffline()) {
+    if (dsConfig.isOffline()) {
       if (config.getDatabasePlatformName() == null) {
         throw new PersistenceException("You MUST specify a DatabasePlatformName on DatabaseConfig when offline");
       }
     }
 
-    attachAlert(dsSettings);
-    attachListener(dsSettings);
+    attachAlert(dsConfig);
+    attachListener(dsConfig);
 
     if (readOnly) {
       // setup to use AutoCommit such that we skip explicit commit
-      var mainSettings = config.getDataSourceConfig().settings();
+      var mainSettings = config.getDataSourceConfig();
       dsConfig.autoCommit(true);
       dsConfig.readOnly(true);
       dsConfig.setDefaults(mainSettings);
diff --git a/ebean-core/src/test/java/io/ebeaninternal/server/core/InitDataSourceTest.java b/ebean-core/src/test/java/io/ebeaninternal/server/core/InitDataSourceTest.java
index 824477d43..3d77ca813 100644
--- a/ebean-core/src/test/java/io/ebeaninternal/server/core/InitDataSourceTest.java
+++ b/ebean-core/src/test/java/io/ebeaninternal/server/core/InitDataSourceTest.java
@@ -127,7 +127,7 @@ public class InitDataSourceTest {
   @Test
   public void readOnlyConfig_when_urlSet_2() {
     DatabaseConfig config = new DatabaseConfig();
-    config.settings().getReadOnlyDataSourceConfig().url("foo");
+    config.getReadOnlyDataSourceConfig().url("foo");
 
     final DataSourceBuilder roConfig = new InitDataSource(config).readOnlyConfig();
     assertNotNull(roConfig);
diff --git a/ebean-test/src/main/java/io/ebean/test/config/AutoConfigureForTesting.java b/ebean-test/src/main/java/io/ebean/test/config/AutoConfigureForTesting.java
index 668eb86bf..be41a5e22 100644
--- a/ebean-test/src/main/java/io/ebean/test/config/AutoConfigureForTesting.java
+++ b/ebean-test/src/main/java/io/ebean/test/config/AutoConfigureForTesting.java
@@ -71,11 +71,11 @@ public class AutoConfigureForTesting implements AutoConfigure {
     }
   }
 
-  private void makeV1Compatible(DataSourceBuilder ds) {
+  private void makeV1Compatible(DataSourceBuilder.Settings ds) {
     if (ds == null) {
       return;
     }
-    String url = ds.settings().getUrl();
+    String url = ds.getUrl();
     if (url == null || !url.startsWith("jdbc:h2:")) {
       return;
     }

From a2551ce71851452c560354c043673391bcad7ff8 Mon Sep 17 00:00:00 2001
From: Rob Bygrave 
Date: Mon, 6 Nov 2023 12:50:14 +1300
Subject: [PATCH 2/2] Bump ebean-datasource to 8.9

---
 pom.xml | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/pom.xml b/pom.xml
index 3ecc6faf3..acf5f046b 100644
--- a/pom.xml
+++ b/pom.xml
@@ -52,7 +52,7 @@
     1.2
     13.11.1
     7.1
-    8.8
+    8.9
     13.24.0
     13.24.0
     false