Skip to content

Commit

Permalink
Allow access to child providers in ChainedConfigurationProvider (#67610)
Browse files Browse the repository at this point in the history
  • Loading branch information
maryamariyan authored Apr 6, 2022
1 parent 548bb58 commit c79c8e1
Show file tree
Hide file tree
Showing 4 changed files with 71 additions and 7 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ public static partial class ChainedBuilderExtensions
public partial class ChainedConfigurationProvider : Microsoft.Extensions.Configuration.IConfigurationProvider, System.IDisposable
{
public ChainedConfigurationProvider(Microsoft.Extensions.Configuration.ChainedConfigurationSource source) { }
public Microsoft.Extensions.Configuration.IConfiguration Configuration { get { throw null; } }
public void Dispose() { }
public System.Collections.Generic.IEnumerable<string> GetChildKeys(System.Collections.Generic.IEnumerable<string> earlierKeys, string? parentPath) { throw null; }
public Microsoft.Extensions.Primitives.IChangeToken GetReloadToken() { throw null; }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,15 +21,15 @@ public class ChainedConfigurationProvider : IConfigurationProvider, IDisposable
/// <param name="source">The source configuration.</param>
public ChainedConfigurationProvider(ChainedConfigurationSource source!!)
{
if (source.Configuration == null)
{
throw new ArgumentException(SR.Format(SR.InvalidNullArgument, "source.Configuration"), nameof(source));
}

_config = source.Configuration;
_config = source.Configuration ?? throw new ArgumentException(SR.Format(SR.InvalidNullArgument, "source.Configuration"), nameof(source));
_shouldDisposeConfig = source.ShouldDisposeConfiguration;
}

/// <summary>
/// Gets the chained configuration.
/// </summary>
public IConfiguration Configuration => _config;

/// <summary>
/// Tries to get a configuration value for the specified key.
/// </summary>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

using System.Collections.Generic;
using System.Linq;
using Microsoft.Extensions.Configuration.Memory;
using Xunit;

namespace Microsoft.Extensions.Configuration.Test
{
public class ChainedConfigurationProvierTests
{
[Fact]
public void ChainedConfiguration_UsingMemoryConfigurationSource_ChainedCouldExposeProvider()
{
var chainedConfigurationProvider = new ChainedConfigurationSource
{
Configuration = new ConfigurationBuilder()
.Add(new MemoryConfigurationSource {
InitialData = new Dictionary<string, string>() { { "a:b", "c" } }
})
.Build(),
ShouldDisposeConfiguration = false,
}
.Build(new ConfigurationBuilder()) as ChainedConfigurationProvider;

Assert.True(chainedConfigurationProvider.TryGet("a:b", out string? value));
Assert.Equal("c", value);
Assert.Equal("c", chainedConfigurationProvider.Configuration["a:b"]);

var configRoot = chainedConfigurationProvider.Configuration as IConfigurationRoot;
Assert.NotNull(configRoot);
Assert.Equal(1, configRoot.Providers.Count());
Assert.IsType<MemoryConfigurationProvider>(configRoot.Providers.First());
}

[Fact]
public void ChainedConfiguration_ExposesProvider()
{
var providers = new IConfigurationProvider[] {
new TestConfigurationProvider("foo", "foo-value")
};
var chainedConfigurationSource = new ChainedConfigurationSource
{
Configuration = new ConfigurationRoot(providers),
ShouldDisposeConfiguration = false,
};

var chainedConfigurationProvider = chainedConfigurationSource
.Build(new ConfigurationBuilder()) as ChainedConfigurationProvider;

var configRoot = chainedConfigurationProvider.Configuration as IConfigurationRoot;
Assert.NotNull(configRoot);
Assert.Equal(providers, configRoot.Providers);
}

private class TestConfigurationProvider : ConfigurationProvider
{
public TestConfigurationProvider(string key, string value)
=> Data.Add(key, value);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -221,7 +221,7 @@ public async Task ProviderDisposeDelayedWaitingOnConcurrentRead(Action<IConfigur

builder.Add(new TestConfigurationSource(provider));

// Reading configuration will block on provider.TryRead() or profvider.GetChildKeys().
// Reading configuration will block on provider.TryRead() or provider.GetChildKeys().
var readTask = Task.Run(() => concurrentReadAction(config));
await provider.ReadStartedTask;

Expand Down

0 comments on commit c79c8e1

Please sign in to comment.