wip(scheduler): compose storage configuration compatibility
Sprint SPRINT_20260417_002_JobEngine_scheduler_storage_compose_compatibility (SCHEDULER-COMPAT-001 still DOING — sprint remains active). Adds scheduler storage configuration adapter layer so the web host accepts the compose-shaped storage configuration without manual remapping, plus SchedulerStorageConfigurationTests. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,32 @@
|
||||
using Microsoft.Extensions.Configuration;
|
||||
|
||||
namespace StellaOps.Scheduler.WebService.Configuration;
|
||||
|
||||
public static class SchedulerStorageConfiguration
|
||||
{
|
||||
public const string FlatSectionPath = "Scheduler:Storage";
|
||||
public const string ComposeNestedSectionPath = "Scheduler:Storage:Postgres:Scheduler";
|
||||
public const string LegacySectionPath = "Postgres:Scheduler";
|
||||
|
||||
public static string? ResolveSectionPath(IConfiguration configuration)
|
||||
{
|
||||
foreach (var sectionPath in GetCandidateSectionPaths())
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(configuration[$"{sectionPath}:ConnectionString"]))
|
||||
{
|
||||
return sectionPath;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public static string? ResolveConnectionString(IConfiguration configuration)
|
||||
{
|
||||
var sectionPath = ResolveSectionPath(configuration);
|
||||
return sectionPath is null ? null : configuration[$"{sectionPath}:ConnectionString"];
|
||||
}
|
||||
|
||||
private static string[] GetCandidateSectionPaths()
|
||||
=> [FlatSectionPath, ComposeNestedSectionPath, LegacySectionPath];
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using StellaOps.Scheduler.WebService.Configuration;
|
||||
|
||||
namespace StellaOps.Scheduler.WebService.Tests;
|
||||
|
||||
public sealed class SchedulerStorageConfigurationTests
|
||||
{
|
||||
[Fact]
|
||||
public void ResolveConnectionString_PrefersFlatSchedulerStorage()
|
||||
{
|
||||
var configuration = BuildConfiguration(
|
||||
[
|
||||
new("Scheduler:Storage:ConnectionString", "Host=flat;Database=scheduler"),
|
||||
new("Scheduler:Storage:Postgres:Scheduler:ConnectionString", "Host=nested;Database=scheduler"),
|
||||
]);
|
||||
|
||||
Assert.Equal(SchedulerStorageConfiguration.FlatSectionPath, SchedulerStorageConfiguration.ResolveSectionPath(configuration));
|
||||
Assert.Equal("Host=flat;Database=scheduler", SchedulerStorageConfiguration.ResolveConnectionString(configuration));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ResolveConnectionString_AcceptsComposeNestedStorage()
|
||||
{
|
||||
var configuration = BuildConfiguration(
|
||||
[
|
||||
new("Scheduler:Storage:Postgres:Scheduler:ConnectionString", "Host=nested;Database=scheduler"),
|
||||
]);
|
||||
|
||||
Assert.Equal(SchedulerStorageConfiguration.ComposeNestedSectionPath, SchedulerStorageConfiguration.ResolveSectionPath(configuration));
|
||||
Assert.Equal("Host=nested;Database=scheduler", SchedulerStorageConfiguration.ResolveConnectionString(configuration));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ResolveConnectionString_FallsBackToLegacyPostgresScheduler()
|
||||
{
|
||||
var configuration = BuildConfiguration(
|
||||
[
|
||||
new("Postgres:Scheduler:ConnectionString", "Host=legacy;Database=scheduler"),
|
||||
]);
|
||||
|
||||
Assert.Equal(SchedulerStorageConfiguration.LegacySectionPath, SchedulerStorageConfiguration.ResolveSectionPath(configuration));
|
||||
Assert.Equal("Host=legacy;Database=scheduler", SchedulerStorageConfiguration.ResolveConnectionString(configuration));
|
||||
}
|
||||
|
||||
private static IConfiguration BuildConfiguration(IEnumerable<KeyValuePair<string, string?>> values)
|
||||
=> new ConfigurationBuilder()
|
||||
.AddInMemoryCollection(values)
|
||||
.Build();
|
||||
}
|
||||
Reference in New Issue
Block a user