Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,7 @@ public DBOSWorkflowRegistrar dbosWorkflowRegistrar(
return new DBOSWorkflowRegistrar(dbos, applicationContext);
}

@SuppressWarnings("removal")
private DBOSConfig buildConfig(DBOSProperties props, String springAppName) {
String appName =
props.getApplication().getName() != null ? props.getApplication().getName() : springAppName;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ void dbosConfigReflectsDatasourceProperties() {
}

@Test
@SuppressWarnings("removal")
void dbosConfigReflectsOptionalProperties() {
runner
.withPropertyValues(
Expand Down
156 changes: 156 additions & 0 deletions transact/src/main/java/dev/dbos/transact/config/DBOSConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,49 @@
import org.jspecify.annotations.NonNull;
import org.jspecify.annotations.Nullable;

/**
* Immutable configuration for a DBOS application instance.
*
* <p>Use {@link #defaults(String)} or {@link #defaultsFromEnv(String)} to obtain a base
* configuration, then chain {@code with*} methods to set individual options:
*
* <pre>{@code
* DBOSConfig config = DBOSConfig.defaults("my-app")
* .withDatabaseUrl("jdbc:postgresql://localhost:5432/mydb")
* .withMigrate(true);
* }</pre>
*
* @param appName unique name for this application; must not be null or empty
* @param databaseUrl JDBC URL of the PostgreSQL database; may be {@code null} when a {@link
* DataSource} is provided instead
* @param dbUser PostgreSQL username; may be {@code null} to rely on driver defaults
* @param dbPassword PostgreSQL password; masked in {@link #toString()}
* @param dataSource pre-configured {@link DataSource} to use instead of {@code databaseUrl}, {@code
* dbUser}, and {@code dbPassword}
* @param adminServer whether to start the built-in admin HTTP server; deprecated and will be
* removed before 1.0 — use DBOS Conductor instead
* @param adminServerPort port for the built-in admin HTTP server; deprecated and will be removed
* before 1.0 — use DBOS Conductor instead
* @param migrate whether to run database migrations on startup
* @param conductorKey API key for DBOS Conductor; must not be empty if non-null
* @param conductorDomain custom hostname for DBOS Conductor; must not be empty if non-null
* @param conductorExecutorMetadata arbitrary key-value metadata attached to this executor's
* registration in Conductor
* @param appVersion application version string used for versioned workflow routing; must not be
* empty if non-null
* @param executorId stable identifier for this executor instance; must not be empty if non-null
* @param databaseSchema PostgreSQL schema used for DBOS system tables; {@code null} uses the
* default schema
* @param enablePatching whether to enable workflow patching
* @param listenQueues names of queues this executor should dequeue work from; an empty set means
* listen on all queues
* @param serializer custom {@link DBOSSerializer} for workflow arguments and return values; {@code
* null} uses the default JSON serializer
* @param schedulerPollingInterval how often the cron scheduler polls for due tasks; {@code null}
* uses the system default
* @param useListenNotify whether to use PostgreSQL {@code LISTEN}/{@code NOTIFY} for real-time
* workflow wake-ups instead of polling
*/
public record DBOSConfig(
@NonNull String appName,
@Nullable String databaseUrl,
Expand Down Expand Up @@ -59,6 +102,24 @@ public record DBOSConfig(
listenQueues = (listenQueues == null) ? Set.of() : Set.copyOf(listenQueues);
}

/**
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
@Override
public boolean adminServer() {
return adminServer;
}

/**
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
@Override
public int adminServerPort() {
return adminServerPort;
}

// Copy constructor
public DBOSConfig(DBOSConfig other) {
this(
Expand All @@ -85,6 +146,16 @@ public DBOSConfig(DBOSConfig other) {
other.useListenNotify);
}

/**
* Returns a {@link DBOSConfig} with sensible defaults for the given application name.
*
* <p>Migrations are enabled and {@code LISTEN}/{@code NOTIFY} is used for workflow wake-ups. No
* database connection details are pre-filled; supply them with {@link #withDatabaseUrl}, {@link
* #withDbUser}/{@link #withDbPassword}, or {@link #withDataSource}.
*
* @param appName unique application name; must not be null or empty
* @return a default {@link DBOSConfig} for the given name
*/
public static @NonNull DBOSConfig defaults(@NonNull String appName) {
return new DBOSConfig(
appName, null, null, null, null, false, // adminServer
Expand All @@ -93,6 +164,20 @@ public DBOSConfig(DBOSConfig other) {
null, null, null, null, null, null, false, null, null, null, true); // useListenNotify
}

/**
* Returns a {@link DBOSConfig} populated from standard environment variables.
*
* <p>Reads the following variables:
*
* <ul>
* <li>{@code DBOS_SYSTEM_JDBC_URL} — JDBC URL for the database
* <li>{@code PGUSER} — database username (defaults to {@code "postgres"} if absent)
* <li>{@code PGPASSWORD} — database password
* </ul>
*
* @param appName unique application name; must not be null or empty
* @return a {@link DBOSConfig} seeded from environment variables
*/
public static @NonNull DBOSConfig defaultsFromEnv(@NonNull String appName) {
String databaseUrl = System.getenv(Constants.SYSTEM_JDBC_URL_ENV_VAR);
String dbUser = System.getenv(Constants.POSTGRES_USER_ENV_VAR);
Expand All @@ -104,6 +189,7 @@ public DBOSConfig(DBOSConfig other) {
.withDbPassword(dbPassword);
}

/** Returns a copy of this config with {@code appName} set to {@code v}. */
public @NonNull DBOSConfig withAppName(@NonNull String v) {
return new DBOSConfig(
v,
Expand All @@ -127,6 +213,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code databaseUrl} set to {@code v}. */
public @NonNull DBOSConfig withDatabaseUrl(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -150,6 +237,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code dbUser} set to {@code v}. */
public @NonNull DBOSConfig withDbUser(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -173,6 +261,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code dbPassword} set to {@code v}. */
public @NonNull DBOSConfig withDbPassword(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -196,6 +285,12 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/**
* Returns a copy of this config with {@code dataSource} set to {@code v}.
*
* <p>When a {@link DataSource} is provided it takes precedence over {@code databaseUrl}, {@code
* dbUser}, and {@code dbPassword}.
*/
public @NonNull DBOSConfig withDataSource(@Nullable DataSource v) {
return new DBOSConfig(
appName,
Expand All @@ -219,6 +314,12 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/**
* Returns a copy of this config with {@code adminServer} set to {@code v}.
*
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
public @NonNull DBOSConfig withAdminServer(boolean v) {
return new DBOSConfig(
appName,
Expand All @@ -242,6 +343,12 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/**
* Returns a copy of this config with {@code adminServerPort} set to {@code v}.
*
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
public @NonNull DBOSConfig withAdminServerPort(int v) {
return new DBOSConfig(
appName,
Expand All @@ -265,6 +372,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code migrate} set to {@code v}. */
public @NonNull DBOSConfig withMigrate(boolean v) {
return new DBOSConfig(
appName,
Expand All @@ -288,6 +396,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code conductorKey} set to {@code v}. */
public @NonNull DBOSConfig withConductorKey(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -311,6 +420,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code conductorDomain} set to {@code v}. */
public @NonNull DBOSConfig withConductorDomain(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -334,6 +444,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code conductorExecutorMetadata} set to {@code v}. */
public @NonNull DBOSConfig withConductorExecutorMetadata(@Nullable Map<String, Object> v) {
return new DBOSConfig(
appName,
Expand All @@ -357,6 +468,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code appVersion} set to {@code v}. */
public @NonNull DBOSConfig withAppVersion(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -380,6 +492,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code executorId} set to {@code v}. */
public @NonNull DBOSConfig withExecutorId(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -403,6 +516,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code databaseSchema} set to {@code v}. */
public @NonNull DBOSConfig withDatabaseSchema(@Nullable String v) {
return new DBOSConfig(
appName,
Expand All @@ -426,14 +540,17 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code enablePatching} set to {@code true}. */
public @NonNull DBOSConfig withEnablePatching() {
return this.withEnablePatching(true);
}

/** Returns a copy of this config with {@code enablePatching} set to {@code false}. */
public @NonNull DBOSConfig withDisablePatching() {
return this.withEnablePatching(false);
}

/** Returns a copy of this config with {@code enablePatching} set to {@code v}. */
public @NonNull DBOSConfig withEnablePatching(boolean v) {
return new DBOSConfig(
appName,
Expand All @@ -457,22 +574,52 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/**
* Returns a copy of this config with the built-in admin server enabled.
*
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
public @NonNull DBOSConfig enableAdminServer() {
return withAdminServer(true);
}

/**
* Returns a copy of this config with the built-in admin server disabled.
*
* @deprecated The built-in admin server will be removed before 1.0. Use DBOS Conductor instead.
*/
@Deprecated(since = "0.9", forRemoval = true)
public @NonNull DBOSConfig disableAdminServer() {
return withAdminServer(false);
}

/**
* Returns a copy of this config with {@code queue} added to the set of listened queues. Removes
* the listen-on-all-queues default if this is the first queue specified.
*
* @param queue the queue to add; must not be null
*/
public @NonNull DBOSConfig withListenQueue(@NonNull Queue queue) {
return withListenQueues(new String[] {queue.name()});
}

/**
* Returns a copy of this config with {@code queueName} added to the set of listened queues.
* Removes the listen-on-all-queues default if this is the first queue specified.
*
* @param queueName the queue name to add; must not be null
*/
public @NonNull DBOSConfig withListenQueue(@NonNull String queueName) {
return withListenQueues(new String[] {queueName});
}

/**
* Returns a copy of this config with each queue in {@code queues} added to the listened set.
* Removes the listen-on-all-queues default if this is the first queue specified.
*
* @param queues the queues to add; {@code null} entries are ignored
*/
public @NonNull DBOSConfig withListenQueues(@Nullable Queue... queues) {
var names =
Arrays.stream(Objects.requireNonNullElseGet(queues, () -> new Queue[0]))
Expand All @@ -481,6 +628,12 @@ public DBOSConfig(DBOSConfig other) {
return withListenQueues(names.toArray(String[]::new));
}

/**
* Returns a copy of this config with each name in {@code queueNames} added to the listened set.
* Removes the listen-on-all-queues default if this is the first queue specified.
*
* @param queueNames the queue names to add; {@code null} entries are ignored
*/
public @NonNull DBOSConfig withListenQueues(@Nullable String... queueNames) {
var v =
Stream.concat(
Expand Down Expand Up @@ -510,6 +663,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code serializer} set to {@code v}. */
public @NonNull DBOSConfig withSerializer(@Nullable DBOSSerializer v) {
return new DBOSConfig(
appName,
Expand All @@ -533,6 +687,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code schedulerPollingInterval} set to {@code v}. */
public @NonNull DBOSConfig withSchedulerPollingInterval(@Nullable Duration v) {
return new DBOSConfig(
appName,
Expand All @@ -556,6 +711,7 @@ public DBOSConfig(DBOSConfig other) {
useListenNotify);
}

/** Returns a copy of this config with {@code useListenNotify} set to {@code v}. */
public @NonNull DBOSConfig withUseListenNotify(boolean v) {
return new DBOSConfig(
appName,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -157,6 +157,7 @@ public DBOSExecutor(DBOSConfig config) {
}
}

@SuppressWarnings("removal")
public void start(
DBOS dbos,
Set<DBOSLifecycleListener> listenerSet,
Expand Down