Repository: aspnet/Configuration
Branch: master
Commit: f64994e06556
Files: 179
Total size: 671.0 KB
Directory structure:
gitextract_p1se3q03/
├── .appveyor.yml
├── .gitattributes
├── .gitignore
├── .travis.yml
├── .vsts-pipelines/
│ └── builds/
│ ├── ci-internal.yml
│ └── ci-public.yml
├── CONTRIBUTING.md
├── Configuration.sln
├── Directory.Build.props
├── Directory.Build.targets
├── LICENSE.txt
├── NuGet.config
├── NuGetPackageVerifier.json
├── README.md
├── build/
│ ├── Key.snk
│ ├── dependencies.props
│ ├── repo.props
│ └── sources.props
├── build.cmd
├── build.sh
├── korebuild-lock.txt
├── korebuild.json
├── run.cmd
├── run.ps1
├── run.sh
├── samples/
│ └── KeyVaultSample/
│ ├── EnvironmentSecretManager.cs
│ ├── KeyVaultSample.csproj
│ ├── Program.cs
│ └── settings.json
├── src/
│ ├── Config/
│ │ ├── ChainedBuilderExtensions.cs
│ │ ├── ChainedConfigurationProvider.cs
│ │ ├── ChainedConfigurationSource.cs
│ │ ├── Config.csproj
│ │ ├── ConfigurationBuilder.cs
│ │ ├── ConfigurationKeyComparer.cs
│ │ ├── ConfigurationProvider.cs
│ │ ├── ConfigurationReloadToken.cs
│ │ ├── ConfigurationRoot.cs
│ │ ├── ConfigurationSection.cs
│ │ ├── MemoryConfigurationBuilderExtensions.cs
│ │ ├── MemoryConfigurationProvider.cs
│ │ ├── MemoryConfigurationSource.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.Abstractions/
│ │ ├── Config.Abstractions.csproj
│ │ ├── ConfigurationExtensions.cs
│ │ ├── ConfigurationPath.cs
│ │ ├── IConfiguration.cs
│ │ ├── IConfigurationBuilder.cs
│ │ ├── IConfigurationProvider.cs
│ │ ├── IConfigurationRoot.cs
│ │ ├── IConfigurationSection.cs
│ │ ├── IConfigurationSource.cs
│ │ └── baseline.netcore.json
│ ├── Config.AzureKeyVault/
│ │ ├── AzureKeyVaultConfigurationExtensions.cs
│ │ ├── AzureKeyVaultConfigurationProvider.cs
│ │ ├── AzureKeyVaultConfigurationSource.cs
│ │ ├── Config.AzureKeyVault.csproj
│ │ ├── DefaultKeyVaultSecretManager.cs
│ │ ├── IKeyVaultClient.cs
│ │ ├── IKeyVaultSecretManager.cs
│ │ ├── KeyVaultClientWrapper.cs
│ │ ├── Properties/
│ │ │ └── AssemblyInfo.cs
│ │ └── baseline.netcore.json
│ ├── Config.Binder/
│ │ ├── BinderOptions.cs
│ │ ├── Config.Binder.csproj
│ │ ├── ConfigurationBinder.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.CommandLine/
│ │ ├── CommandLineConfigurationExtensions.cs
│ │ ├── CommandLineConfigurationProvider.cs
│ │ ├── CommandLineConfigurationSource.cs
│ │ ├── Config.CommandLine.csproj
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.EnvironmentVariables/
│ │ ├── Config.EnvironmentVariables.csproj
│ │ ├── EnvironmentVariablesConfigurationProvider.cs
│ │ ├── EnvironmentVariablesConfigurationSource.cs
│ │ ├── EnvironmentVariablesExtensions.cs
│ │ ├── Properties/
│ │ │ └── AssemblyInfo.cs
│ │ └── baseline.netcore.json
│ ├── Config.FileExtensions/
│ │ ├── Config.FileExtensions.csproj
│ │ ├── FileConfigurationExtensions.cs
│ │ ├── FileConfigurationProvider.cs
│ │ ├── FileConfigurationSource.cs
│ │ ├── FileLoadExceptionContext.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.Ini/
│ │ ├── Config.Ini.csproj
│ │ ├── IniConfigurationExtensions.cs
│ │ ├── IniConfigurationProvider.cs
│ │ ├── IniConfigurationSource.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.Json/
│ │ ├── Config.Json.csproj
│ │ ├── JsonConfigurationExtensions.cs
│ │ ├── JsonConfigurationFileParser.cs
│ │ ├── JsonConfigurationProvider.cs
│ │ ├── JsonConfigurationSource.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ └── baseline.netcore.json
│ ├── Config.KeyPerFile/
│ │ ├── Config.KeyPerFile.csproj
│ │ ├── KeyPerFileConfigurationBuilderExtensions.cs
│ │ ├── KeyPerFileConfigurationProvider.cs
│ │ ├── KeyPerFileConfigurationSource.cs
│ │ └── README.md
│ ├── Config.UserSecrets/
│ │ ├── Config.UserSecrets.csproj
│ │ ├── PathHelper.cs
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ ├── UserSecretsConfigurationExtensions.cs
│ │ ├── UserSecretsIdAttribute.cs
│ │ ├── baseline.netcore.json
│ │ └── build/
│ │ └── netstandard2.0/
│ │ ├── Microsoft.Extensions.Configuration.UserSecrets.props
│ │ └── Microsoft.Extensions.Configuration.UserSecrets.targets
│ ├── Config.Xml/
│ │ ├── Config.Xml.csproj
│ │ ├── Properties/
│ │ │ ├── AssemblyInfo.cs
│ │ │ └── Resources.Designer.cs
│ │ ├── Resources.resx
│ │ ├── XmlConfigurationExtensions.cs
│ │ ├── XmlConfigurationProvider.cs
│ │ ├── XmlConfigurationSource.cs
│ │ ├── XmlDocumentDecryptor.cs
│ │ └── baseline.netcore.json
│ └── Directory.Build.props
├── test/
│ ├── Config.AzureKeyVault.Test/
│ │ ├── AzureKeyVaultConfigurationTest.cs
│ │ └── Config.AzureKeyVault.Test.csproj
│ ├── Config.Binder.Test/
│ │ ├── Config.Binder.Test.csproj
│ │ ├── ConfigurationBinderTests.cs
│ │ └── ConfigurationCollectionBindingTests.cs
│ ├── Config.CommandLine.Test/
│ │ ├── CommandLineTest.cs
│ │ └── Config.CommandLine.Test.csproj
│ ├── Config.EnvironmentVariables.Test/
│ │ ├── Config.EnvironmentVariables.Test.csproj
│ │ └── EnvironmentVariablesTest.cs
│ ├── Config.FileExtensions.Test/
│ │ ├── Config.FileExtensions.Test.csproj
│ │ └── FileConfigurationBuilderExtensionsTest.cs
│ ├── Config.FunctionalTests/
│ │ ├── ArrayTests.cs
│ │ ├── Config.FunctionalTests.csproj
│ │ ├── ConfigurationTests.cs
│ │ ├── DisposableFileSystem.cs
│ │ └── test.xml
│ ├── Config.Ini.Test/
│ │ ├── Config.Ini.Test.csproj
│ │ ├── IniConfigurationExtensionsTest.cs
│ │ └── IniConfigurationTest.cs
│ ├── Config.Json.Test/
│ │ ├── ArrayTest.cs
│ │ ├── Config.Json.Test.csproj
│ │ ├── JsonConfigurationExtensionsTest.cs
│ │ └── JsonConfigurationTest.cs
│ ├── Config.KeyPerFile.Test/
│ │ ├── Config.KeyPerFile.Test.csproj
│ │ └── KeyPerFileTests.cs
│ ├── Config.Test/
│ │ ├── Config.Test.csproj
│ │ ├── ConfigurationPathComparerTest.cs
│ │ ├── ConfigurationPathTest.cs
│ │ └── ConfigurationTest.cs
│ ├── Config.Test.Common/
│ │ ├── Config.Test.Common.csproj
│ │ ├── ConfigurationProviderExtensions.cs
│ │ └── TestStreamHelpers.cs
│ ├── Config.UserSecrets.Test/
│ │ ├── Config.UserSecrets.Test.csproj
│ │ ├── ConfigurationExtensionTest.cs
│ │ ├── MsBuildTargetTest.cs
│ │ └── PathHelperTest.cs
│ ├── Config.Xml.Test/
│ │ ├── Config.Xml.Test.csproj
│ │ ├── XmlConfigurationExtensionsTest.cs
│ │ └── XmlConfigurationTest.cs
│ └── Directory.Build.props
└── version.props
================================================
FILE CONTENTS
================================================
================================================
FILE: .appveyor.yml
================================================
init:
- git config --global core.autocrlf true
branches:
only:
- master
- /^release\/.*$/
- /^(.*\/)?ci-.*$/
build_script:
- ps: .\run.ps1 default-build
clone_depth: 1
environment:
global:
DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
DOTNET_CLI_TELEMETRY_OPTOUT: 1
test: 'off'
deploy: 'off'
os: Visual Studio 2017
================================================
FILE: .gitattributes
================================================
*.doc diff=astextplain
*.DOC diff=astextplain
*.docx diff=astextplain
*.DOCX diff=astextplain
*.dot diff=astextplain
*.DOT diff=astextplain
*.pdf diff=astextplain
*.PDF diff=astextplain
*.rtf diff=astextplain
*.RTF diff=astextplain
*.jpg binary
*.png binary
*.gif binary
*.cs text=auto diff=csharp
*.vb text=auto
*.resx text=auto
*.c text=auto
*.cpp text=auto
*.cxx text=auto
*.h text=auto
*.hxx text=auto
*.py text=auto
*.rb text=auto
*.java text=auto
*.html text=auto
*.htm text=auto
*.css text=auto
*.scss text=auto
*.sass text=auto
*.less text=auto
*.js text=auto
*.lisp text=auto
*.clj text=auto
*.sql text=auto
*.php text=auto
*.lua text=auto
*.m text=auto
*.asm text=auto
*.erl text=auto
*.fs text=auto
*.fsx text=auto
*.hs text=auto
*.csproj text=auto
*.vbproj text=auto
*.fsproj text=auto
*.dbproj text=auto
*.sln text=auto eol=crlf
*.sh eol=lf
================================================
FILE: .gitignore
================================================
[Oo]bj/
[Bb]in/
TestResults/
.nuget/
_ReSharper.*/
packages/
artifacts/
PublishProfiles/
*.user
*.suo
*.cache
*.docstates
_ReSharper.*
nuget.exe
*net45.csproj
*net451.csproj
*k10.csproj
*.psess
*.vsp
*.pidb
*.userprefs
*DS_Store
*.ncrunchsolution
*.*sdf
*.ipch
*.sln.ide
project.lock.json
.vs
.vscode/
.build/
.testPublish/
*.nuget.props
*.nuget.targets
global.json
================================================
FILE: .travis.yml
================================================
language: csharp
sudo: false
dist: trusty
env:
global:
- DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
- DOTNET_CLI_TELEMETRY_OPTOUT: 1
mono: none
os:
- linux
- osx
osx_image: xcode8.2
addons:
apt:
packages:
- libunwind8
branches:
only:
- master
- /^release\/.*$/
- /^(.*\/)?ci-.*$/
before_install:
- if test "$TRAVIS_OS_NAME" == "osx"; then brew update; brew install openssl; ln -s
/usr/local/opt/openssl/lib/libcrypto.1.0.0.dylib /usr/local/lib/; ln -s /usr/local/opt/openssl/lib/libssl.1.0.0.dylib
/usr/local/lib/; fi
script:
- ./build.sh
================================================
FILE: .vsts-pipelines/builds/ci-internal.yml
================================================
trigger:
- master
- release/*
resources:
repositories:
- repository: buildtools
type: git
name: aspnet-BuildTools
ref: refs/heads/master
phases:
- template: .vsts-pipelines/templates/project-ci.yml@buildtools
================================================
FILE: .vsts-pipelines/builds/ci-public.yml
================================================
trigger:
- master
- release/*
# See https://github.com/aspnet/BuildTools
resources:
repositories:
- repository: buildtools
type: github
endpoint: DotNet-Bot GitHub Connection
name: aspnet/BuildTools
ref: refs/heads/master
phases:
- template: .vsts-pipelines/templates/project-ci.yml@buildtools
================================================
FILE: CONTRIBUTING.md
================================================
Contributing
======
Information on contributing to this repo is in the [Contributing Guide](https://github.com/aspnet/Home/blob/master/CONTRIBUTING.md) in the Home repo.
================================================
FILE: Configuration.sln
================================================
Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 15
VisualStudioVersion = 15.0.26424.2
MinimumVisualStudioVersion = 15.0.26730.03
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}"
ProjectSection(SolutionItems) = preProject
src\Directory.Build.props = src\Directory.Build.props
EndProjectSection
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "test", "test", "{B54371FF-B920-46C8-8D55-6B19DBB43EBF}"
ProjectSection(SolutionItems) = preProject
test\Directory.Build.props = test\Directory.Build.props
EndProjectSection
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Json", "src\Config.Json\Config.Json.csproj", "{4C4CD1BC-4411-4AFD-9D04-147053F0E259}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Xml", "src\Config.Xml\Config.Xml.csproj", "{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Json.Test", "test\Config.Json.Test\Config.Json.Test.csproj", "{AE8F8C20-9ED9-4A16-9565-27DF77683789}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Xml.Test", "test\Config.Xml.Test\Config.Xml.Test.csproj", "{0786C785-944A-4423-96A6-4E7BFDB4A1B0}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Test", "test\Config.Test\Config.Test.csproj", "{8777C77E-CA2A-42C1-90CD-2EA9CBF28937}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration", "src\Config\Config.csproj", "{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.FunctionalTests", "test\Config.FunctionalTests\Config.FunctionalTests.csproj", "{EAC77F15-F12E-496B-9184-1B1DA89BFFE9}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Abstractions", "src\Config.Abstractions\Config.Abstractions.csproj", "{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Test.Common", "test\Config.Test.Common\Config.Test.Common.csproj", "{29C120E5-F682-4BFB-826B-040A594802CA}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.CommandLine", "src\Config.CommandLine\Config.CommandLine.csproj", "{D4B7CF9B-4229-44DC-800F-CC39150CEAB2}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Ini", "src\Config.Ini\Config.Ini.csproj", "{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.EnvironmentVariables", "src\Config.EnvironmentVariables\Config.EnvironmentVariables.csproj", "{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.CommandLine.Test", "test\Config.CommandLine.Test\Config.CommandLine.Test.csproj", "{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Ini.Test", "test\Config.Ini.Test\Config.Ini.Test.csproj", "{80A8F10C-E9A6-4677-919D-FE5DB320FEDF}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.EnvironmentVariables.Test", "test\Config.EnvironmentVariables.Test\Config.EnvironmentVariables.Test.csproj", "{7D0F805B-ADFF-4C47-A90C-24DD74416821}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Binder", "src\Config.Binder\Config.Binder.csproj", "{D506FD2F-59A0-4A26-AA6D-E81998B58B34}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.Binder.Test", "test\Config.Binder.Test\Config.Binder.Test.csproj", "{AE6FFE9B-6378-4D57-AA24-7D257F18B235}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.FileExtensions", "src\Config.FileExtensions\Config.FileExtensions.csproj", "{881E7CBC-492C-47C5-98A6-61DD1C753EE6}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.FileExtensions.Test", "test\Config.FileExtensions.Test\Config.FileExtensions.Test.csproj", "{F7932F19-EB68-4C52-9CD1-3B51E48C2337}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.AzureKeyVault", "src\Config.AzureKeyVault\Config.AzureKeyVault.csproj", "{A538F609-E902-40CE-8459-4248F9F63558}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.AzureKeyVault.Test", "test\Config.AzureKeyVault.Test\Config.AzureKeyVault.Test.csproj", "{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "samples", "samples", "{AB015580-541D-4E2D-B904-E71F8582CC68}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "KeyVaultSample", "samples\KeyVaultSample\KeyVaultSample.csproj", "{7AAC49A7-939A-40B1-A86A-705464B4667D}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.UserSecrets", "src\Config.UserSecrets\Config.UserSecrets.csproj", "{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.UserSecrets.Test", "test\Config.UserSecrets.Test\Config.UserSecrets.Test.csproj", "{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.KeyPerFile", "src\Config.KeyPerFile\Config.KeyPerFile.csproj", "{69AB0230-D82E-438B-AFE5-85BFF414F1B8}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Extensions.Configuration.KeyPerFile.Test", "test\Config.KeyPerFile.Test\Config.KeyPerFile.Test.csproj", "{82A403ED-F827-4FED-BE38-7F87925A07E1}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{B926267F-98A3-41F0-90F5-0B1ADF78CA65}"
ProjectSection(SolutionItems) = preProject
.appveyor.yml = .appveyor.yml
.travis.yml = .travis.yml
build.cmd = build.cmd
build.ps1 = build.ps1
build.sh = build.sh
CONTRIBUTING.md = CONTRIBUTING.md
Directory.Build.props = Directory.Build.props
Directory.Build.targets = Directory.Build.targets
LICENSE.txt = LICENSE.txt
NuGet.config = NuGet.config
NuGetPackageVerifier.json = NuGetPackageVerifier.json
README.md = README.md
version.xml = version.xml
EndProjectSection
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "build", "build", "{F786716B-DE4D-4C4D-8D5B-38182329E5B5}"
ProjectSection(SolutionItems) = preProject
build\dependencies.props = build\dependencies.props
build\repo.props = build\repo.props
EndProjectSection
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{4C4CD1BC-4411-4AFD-9D04-147053F0E259}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{4C4CD1BC-4411-4AFD-9D04-147053F0E259}.Debug|Any CPU.Build.0 = Debug|Any CPU
{4C4CD1BC-4411-4AFD-9D04-147053F0E259}.Release|Any CPU.ActiveCfg = Release|Any CPU
{4C4CD1BC-4411-4AFD-9D04-147053F0E259}.Release|Any CPU.Build.0 = Release|Any CPU
{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A}.Debug|Any CPU.Build.0 = Debug|Any CPU
{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A}.Release|Any CPU.ActiveCfg = Release|Any CPU
{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A}.Release|Any CPU.Build.0 = Release|Any CPU
{AE8F8C20-9ED9-4A16-9565-27DF77683789}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{AE8F8C20-9ED9-4A16-9565-27DF77683789}.Debug|Any CPU.Build.0 = Debug|Any CPU
{AE8F8C20-9ED9-4A16-9565-27DF77683789}.Release|Any CPU.ActiveCfg = Release|Any CPU
{AE8F8C20-9ED9-4A16-9565-27DF77683789}.Release|Any CPU.Build.0 = Release|Any CPU
{0786C785-944A-4423-96A6-4E7BFDB4A1B0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{0786C785-944A-4423-96A6-4E7BFDB4A1B0}.Debug|Any CPU.Build.0 = Debug|Any CPU
{0786C785-944A-4423-96A6-4E7BFDB4A1B0}.Release|Any CPU.ActiveCfg = Release|Any CPU
{0786C785-944A-4423-96A6-4E7BFDB4A1B0}.Release|Any CPU.Build.0 = Release|Any CPU
{8777C77E-CA2A-42C1-90CD-2EA9CBF28937}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8777C77E-CA2A-42C1-90CD-2EA9CBF28937}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8777C77E-CA2A-42C1-90CD-2EA9CBF28937}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8777C77E-CA2A-42C1-90CD-2EA9CBF28937}.Release|Any CPU.Build.0 = Release|Any CPU
{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1}.Debug|Any CPU.Build.0 = Debug|Any CPU
{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1}.Release|Any CPU.ActiveCfg = Release|Any CPU
{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1}.Release|Any CPU.Build.0 = Release|Any CPU
{EAC77F15-F12E-496B-9184-1B1DA89BFFE9}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{EAC77F15-F12E-496B-9184-1B1DA89BFFE9}.Debug|Any CPU.Build.0 = Debug|Any CPU
{EAC77F15-F12E-496B-9184-1B1DA89BFFE9}.Release|Any CPU.ActiveCfg = Release|Any CPU
{EAC77F15-F12E-496B-9184-1B1DA89BFFE9}.Release|Any CPU.Build.0 = Release|Any CPU
{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49}.Debug|Any CPU.Build.0 = Debug|Any CPU
{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49}.Release|Any CPU.ActiveCfg = Release|Any CPU
{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49}.Release|Any CPU.Build.0 = Release|Any CPU
{29C120E5-F682-4BFB-826B-040A594802CA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{29C120E5-F682-4BFB-826B-040A594802CA}.Debug|Any CPU.Build.0 = Debug|Any CPU
{29C120E5-F682-4BFB-826B-040A594802CA}.Release|Any CPU.ActiveCfg = Release|Any CPU
{29C120E5-F682-4BFB-826B-040A594802CA}.Release|Any CPU.Build.0 = Release|Any CPU
{D4B7CF9B-4229-44DC-800F-CC39150CEAB2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{D4B7CF9B-4229-44DC-800F-CC39150CEAB2}.Debug|Any CPU.Build.0 = Debug|Any CPU
{D4B7CF9B-4229-44DC-800F-CC39150CEAB2}.Release|Any CPU.ActiveCfg = Release|Any CPU
{D4B7CF9B-4229-44DC-800F-CC39150CEAB2}.Release|Any CPU.Build.0 = Release|Any CPU
{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7}.Debug|Any CPU.Build.0 = Debug|Any CPU
{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7}.Release|Any CPU.ActiveCfg = Release|Any CPU
{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7}.Release|Any CPU.Build.0 = Release|Any CPU
{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88}.Debug|Any CPU.Build.0 = Debug|Any CPU
{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88}.Release|Any CPU.ActiveCfg = Release|Any CPU
{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88}.Release|Any CPU.Build.0 = Release|Any CPU
{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF}.Debug|Any CPU.Build.0 = Debug|Any CPU
{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF}.Release|Any CPU.ActiveCfg = Release|Any CPU
{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF}.Release|Any CPU.Build.0 = Release|Any CPU
{80A8F10C-E9A6-4677-919D-FE5DB320FEDF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{80A8F10C-E9A6-4677-919D-FE5DB320FEDF}.Debug|Any CPU.Build.0 = Debug|Any CPU
{80A8F10C-E9A6-4677-919D-FE5DB320FEDF}.Release|Any CPU.ActiveCfg = Release|Any CPU
{80A8F10C-E9A6-4677-919D-FE5DB320FEDF}.Release|Any CPU.Build.0 = Release|Any CPU
{7D0F805B-ADFF-4C47-A90C-24DD74416821}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{7D0F805B-ADFF-4C47-A90C-24DD74416821}.Debug|Any CPU.Build.0 = Debug|Any CPU
{7D0F805B-ADFF-4C47-A90C-24DD74416821}.Release|Any CPU.ActiveCfg = Release|Any CPU
{7D0F805B-ADFF-4C47-A90C-24DD74416821}.Release|Any CPU.Build.0 = Release|Any CPU
{D506FD2F-59A0-4A26-AA6D-E81998B58B34}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{D506FD2F-59A0-4A26-AA6D-E81998B58B34}.Debug|Any CPU.Build.0 = Debug|Any CPU
{D506FD2F-59A0-4A26-AA6D-E81998B58B34}.Release|Any CPU.ActiveCfg = Release|Any CPU
{D506FD2F-59A0-4A26-AA6D-E81998B58B34}.Release|Any CPU.Build.0 = Release|Any CPU
{AE6FFE9B-6378-4D57-AA24-7D257F18B235}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{AE6FFE9B-6378-4D57-AA24-7D257F18B235}.Debug|Any CPU.Build.0 = Debug|Any CPU
{AE6FFE9B-6378-4D57-AA24-7D257F18B235}.Release|Any CPU.ActiveCfg = Release|Any CPU
{AE6FFE9B-6378-4D57-AA24-7D257F18B235}.Release|Any CPU.Build.0 = Release|Any CPU
{881E7CBC-492C-47C5-98A6-61DD1C753EE6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{881E7CBC-492C-47C5-98A6-61DD1C753EE6}.Debug|Any CPU.Build.0 = Debug|Any CPU
{881E7CBC-492C-47C5-98A6-61DD1C753EE6}.Release|Any CPU.ActiveCfg = Release|Any CPU
{881E7CBC-492C-47C5-98A6-61DD1C753EE6}.Release|Any CPU.Build.0 = Release|Any CPU
{F7932F19-EB68-4C52-9CD1-3B51E48C2337}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{F7932F19-EB68-4C52-9CD1-3B51E48C2337}.Debug|Any CPU.Build.0 = Debug|Any CPU
{F7932F19-EB68-4C52-9CD1-3B51E48C2337}.Release|Any CPU.ActiveCfg = Release|Any CPU
{F7932F19-EB68-4C52-9CD1-3B51E48C2337}.Release|Any CPU.Build.0 = Release|Any CPU
{A538F609-E902-40CE-8459-4248F9F63558}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{A538F609-E902-40CE-8459-4248F9F63558}.Debug|Any CPU.Build.0 = Debug|Any CPU
{A538F609-E902-40CE-8459-4248F9F63558}.Release|Any CPU.ActiveCfg = Release|Any CPU
{A538F609-E902-40CE-8459-4248F9F63558}.Release|Any CPU.Build.0 = Release|Any CPU
{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48}.Debug|Any CPU.Build.0 = Debug|Any CPU
{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48}.Release|Any CPU.ActiveCfg = Release|Any CPU
{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48}.Release|Any CPU.Build.0 = Release|Any CPU
{7AAC49A7-939A-40B1-A86A-705464B4667D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{7AAC49A7-939A-40B1-A86A-705464B4667D}.Debug|Any CPU.Build.0 = Debug|Any CPU
{7AAC49A7-939A-40B1-A86A-705464B4667D}.Release|Any CPU.ActiveCfg = Release|Any CPU
{7AAC49A7-939A-40B1-A86A-705464B4667D}.Release|Any CPU.Build.0 = Release|Any CPU
{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868}.Debug|Any CPU.Build.0 = Debug|Any CPU
{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868}.Release|Any CPU.ActiveCfg = Release|Any CPU
{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868}.Release|Any CPU.Build.0 = Release|Any CPU
{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A}.Debug|Any CPU.Build.0 = Debug|Any CPU
{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A}.Release|Any CPU.ActiveCfg = Release|Any CPU
{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A}.Release|Any CPU.Build.0 = Release|Any CPU
{69AB0230-D82E-438B-AFE5-85BFF414F1B8}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{69AB0230-D82E-438B-AFE5-85BFF414F1B8}.Debug|Any CPU.Build.0 = Debug|Any CPU
{69AB0230-D82E-438B-AFE5-85BFF414F1B8}.Release|Any CPU.ActiveCfg = Release|Any CPU
{69AB0230-D82E-438B-AFE5-85BFF414F1B8}.Release|Any CPU.Build.0 = Release|Any CPU
{82A403ED-F827-4FED-BE38-7F87925A07E1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{82A403ED-F827-4FED-BE38-7F87925A07E1}.Debug|Any CPU.Build.0 = Debug|Any CPU
{82A403ED-F827-4FED-BE38-7F87925A07E1}.Release|Any CPU.ActiveCfg = Release|Any CPU
{82A403ED-F827-4FED-BE38-7F87925A07E1}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(NestedProjects) = preSolution
{4C4CD1BC-4411-4AFD-9D04-147053F0E259} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{1BEC97C1-56B9-4B2B-A95A-C0DF72F1E96A} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{AE8F8C20-9ED9-4A16-9565-27DF77683789} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{0786C785-944A-4423-96A6-4E7BFDB4A1B0} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{8777C77E-CA2A-42C1-90CD-2EA9CBF28937} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{62BD48B5-BB0C-4C2C-9C4B-04CF75CDCCF1} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{EAC77F15-F12E-496B-9184-1B1DA89BFFE9} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{3F1CB08E-9FBD-4CAE-A78A-4AC43F24FC49} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{29C120E5-F682-4BFB-826B-040A594802CA} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{D4B7CF9B-4229-44DC-800F-CC39150CEAB2} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{C555C5D5-BF4A-451E-AB43-EBF4DE885EC7} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{A6A2C665-E5A4-4FD3-AD0C-E33E6CFFCB88} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{CE9C8903-AA8A-40E6-B03D-32A08A4A39AF} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{80A8F10C-E9A6-4677-919D-FE5DB320FEDF} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{7D0F805B-ADFF-4C47-A90C-24DD74416821} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{D506FD2F-59A0-4A26-AA6D-E81998B58B34} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{AE6FFE9B-6378-4D57-AA24-7D257F18B235} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{881E7CBC-492C-47C5-98A6-61DD1C753EE6} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{F7932F19-EB68-4C52-9CD1-3B51E48C2337} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{A538F609-E902-40CE-8459-4248F9F63558} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{DA9C1F35-3F92-4F3A-B3B1-A62CCE626D48} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{7AAC49A7-939A-40B1-A86A-705464B4667D} = {AB015580-541D-4E2D-B904-E71F8582CC68}
{58B6443B-1278-4DF9-B7BB-DDF3BFFCF868} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{AC7FAD2A-5763-404D-B0FC-3CCA81A16B0A} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{69AB0230-D82E-438B-AFE5-85BFF414F1B8} = {F141E2D0-F9B8-4ADB-A19A-7B6FF4CA19A1}
{82A403ED-F827-4FED-BE38-7F87925A07E1} = {B54371FF-B920-46C8-8D55-6B19DBB43EBF}
{F786716B-DE4D-4C4D-8D5B-38182329E5B5} = {B926267F-98A3-41F0-90F5-0B1ADF78CA65}
EndGlobalSection
EndGlobal
================================================
FILE: Directory.Build.props
================================================
Microsoft .NET Extensions
https://github.com/aspnet/Configuration
git
$(MSBuildThisFileDirectory)
$(MSBuildThisFileDirectory)build\Key.snk
true
true
================================================
FILE: Directory.Build.targets
================================================
$(MicrosoftNETCoreApp20PackageVersion)
$(MicrosoftNETCoreApp21PackageVersion)
$(MicrosoftNETCoreApp22PackageVersion)
$(NETStandardLibrary20PackageVersion)
99.9
================================================
FILE: LICENSE.txt
================================================
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright (c) .NET Foundation and Contributors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
================================================
FILE: NuGet.config
================================================
================================================
FILE: NuGetPackageVerifier.json
================================================
{
"Default": {
"rules": [
"DefaultCompositeRule"
]
}
}
================================================
FILE: README.md
================================================
Configuration [Archived]
========================
**This GitHub project has been archived.** Ongoing development on this project can be found in .
Configuration is a framework for accessing Key/Value based configuration settings in an application. Includes configuration providers for command line arguments, environment variables, INI files, JSON files, and XML files.
This project is part of ASP.NET Core. You can find samples, documentation and getting started instructions for ASP.NET Core at the [AspNetCore](https://github.com/aspnet/AspNetCore) repo.
================================================
FILE: build/dependencies.props
================================================
$(MSBuildAllProjects);$(MSBuildThisFileFullPath)
3.0.0-alpha1-20181004.7
3.0.0-alpha1-10584
2.3.2
1.0.1
3.0.0-alpha1-10584
3.0.0-alpha1-10584
2.0.9
2.1.3
2.2.0-preview2-26905-02
15.6.1
4.9.0
2.0.3
11.0.2
4.6.0-preview1-26907-04
2.3.1
2.4.0
================================================
FILE: build/repo.props
================================================
Internal.AspNetCore.Universe.Lineup
https://dotnet.myget.org/F/aspnetcore-dev/api/v3/index.json
================================================
FILE: build/sources.props
================================================
$(DotNetRestoreSources)
$(RestoreSources);
https://dotnet.myget.org/F/dotnet-core/api/v3/index.json;
https://dotnet.myget.org/F/aspnetcore-dev/api/v3/index.json;
https://dotnet.myget.org/F/aspnetcore-tools/api/v3/index.json;
$(RestoreSources);
https://api.nuget.org/v3/index.json;
================================================
FILE: build.cmd
================================================
@ECHO OFF
PowerShell -NoProfile -NoLogo -ExecutionPolicy unrestricted -Command "[System.Threading.Thread]::CurrentThread.CurrentCulture = ''; [System.Threading.Thread]::CurrentThread.CurrentUICulture = '';& '%~dp0run.ps1' default-build %*; exit $LASTEXITCODE"
================================================
FILE: build.sh
================================================
#!/usr/bin/env bash
set -euo pipefail
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
# Call "sync" between "chmod" and execution to prevent "text file busy" error in Docker (aufs)
chmod +x "$DIR/run.sh"; sync
"$DIR/run.sh" default-build "$@"
================================================
FILE: korebuild-lock.txt
================================================
version:3.0.0-alpha1-20181004.7
commithash:27fabdaf2b1d4753c3d2749581694ca65d78f7f2
================================================
FILE: korebuild.json
================================================
{
"$schema": "https://raw.githubusercontent.com/aspnet/BuildTools/master/tools/korebuild.schema.json",
"channel": "master"
}
================================================
FILE: run.cmd
================================================
@ECHO OFF
PowerShell -NoProfile -NoLogo -ExecutionPolicy unrestricted -Command "[System.Threading.Thread]::CurrentThread.CurrentCulture = ''; [System.Threading.Thread]::CurrentThread.CurrentUICulture = '';& '%~dp0run.ps1' %*; exit $LASTEXITCODE"
================================================
FILE: run.ps1
================================================
#!/usr/bin/env powershell
#requires -version 4
<#
.SYNOPSIS
Executes KoreBuild commands.
.DESCRIPTION
Downloads korebuild if required. Then executes the KoreBuild command. To see available commands, execute with `-Command help`.
.PARAMETER Command
The KoreBuild command to run.
.PARAMETER Path
The folder to build. Defaults to the folder containing this script.
.PARAMETER Channel
The channel of KoreBuild to download. Overrides the value from the config file.
.PARAMETER DotNetHome
The directory where .NET Core tools will be stored.
.PARAMETER ToolsSource
The base url where build tools can be downloaded. Overrides the value from the config file.
.PARAMETER Update
Updates KoreBuild to the latest version even if a lock file is present.
.PARAMETER Reinstall
Re-installs KoreBuild
.PARAMETER ConfigFile
The path to the configuration file that stores values. Defaults to korebuild.json.
.PARAMETER ToolsSourceSuffix
The Suffix to append to the end of the ToolsSource. Useful for query strings in blob stores.
.PARAMETER CI
Sets up CI specific settings and variables.
.PARAMETER Arguments
Arguments to be passed to the command
.NOTES
This function will create a file $PSScriptRoot/korebuild-lock.txt. This lock file can be committed to source, but does not have to be.
When the lockfile is not present, KoreBuild will create one using latest available version from $Channel.
The $ConfigFile is expected to be an JSON file. It is optional, and the configuration values in it are optional as well. Any options set
in the file are overridden by command line parameters.
.EXAMPLE
Example config file:
```json
{
"$schema": "https://raw.githubusercontent.com/aspnet/BuildTools/master/tools/korebuild.schema.json",
"channel": "master",
"toolsSource": "https://aspnetcore.blob.core.windows.net/buildtools"
}
```
#>
[CmdletBinding(PositionalBinding = $false)]
param(
[Parameter(Mandatory = $true, Position = 0)]
[string]$Command,
[string]$Path = $PSScriptRoot,
[Alias('c')]
[string]$Channel,
[Alias('d')]
[string]$DotNetHome,
[Alias('s')]
[string]$ToolsSource,
[Alias('u')]
[switch]$Update,
[switch]$Reinstall,
[string]$ToolsSourceSuffix,
[string]$ConfigFile = $null,
[switch]$CI,
[Parameter(ValueFromRemainingArguments = $true)]
[string[]]$Arguments
)
Set-StrictMode -Version 2
$ErrorActionPreference = 'Stop'
#
# Functions
#
function Get-KoreBuild {
$lockFile = Join-Path $Path 'korebuild-lock.txt'
if (!(Test-Path $lockFile) -or $Update) {
Get-RemoteFile "$ToolsSource/korebuild/channels/$Channel/latest.txt" $lockFile $ToolsSourceSuffix
}
$version = Get-Content $lockFile | Where-Object { $_ -like 'version:*' } | Select-Object -first 1
if (!$version) {
Write-Error "Failed to parse version from $lockFile. Expected a line that begins with 'version:'"
}
$version = $version.TrimStart('version:').Trim()
$korebuildPath = Join-Paths $DotNetHome ('buildtools', 'korebuild', $version)
if ($Reinstall -and (Test-Path $korebuildPath)) {
Remove-Item -Force -Recurse $korebuildPath
}
if (!(Test-Path $korebuildPath)) {
Write-Host -ForegroundColor Magenta "Downloading KoreBuild $version"
New-Item -ItemType Directory -Path $korebuildPath | Out-Null
$remotePath = "$ToolsSource/korebuild/artifacts/$version/korebuild.$version.zip"
try {
$tmpfile = Join-Path ([IO.Path]::GetTempPath()) "KoreBuild-$([guid]::NewGuid()).zip"
Get-RemoteFile $remotePath $tmpfile $ToolsSourceSuffix
if (Get-Command -Name 'Microsoft.PowerShell.Archive\Expand-Archive' -ErrorAction Ignore) {
# Use built-in commands where possible as they are cross-plat compatible
Microsoft.PowerShell.Archive\Expand-Archive -Path $tmpfile -DestinationPath $korebuildPath
}
else {
# Fallback to old approach for old installations of PowerShell
Add-Type -AssemblyName System.IO.Compression.FileSystem
[System.IO.Compression.ZipFile]::ExtractToDirectory($tmpfile, $korebuildPath)
}
}
catch {
Remove-Item -Recurse -Force $korebuildPath -ErrorAction Ignore
throw
}
finally {
Remove-Item $tmpfile -ErrorAction Ignore
}
}
return $korebuildPath
}
function Join-Paths([string]$path, [string[]]$childPaths) {
$childPaths | ForEach-Object { $path = Join-Path $path $_ }
return $path
}
function Get-RemoteFile([string]$RemotePath, [string]$LocalPath, [string]$RemoteSuffix) {
if ($RemotePath -notlike 'http*') {
Copy-Item $RemotePath $LocalPath
return
}
$retries = 10
while ($retries -gt 0) {
$retries -= 1
try {
Invoke-WebRequest -UseBasicParsing -Uri $($RemotePath + $RemoteSuffix) -OutFile $LocalPath
return
}
catch {
Write-Verbose "Request failed. $retries retries remaining"
}
}
Write-Error "Download failed: '$RemotePath'."
}
#
# Main
#
# Load configuration or set defaults
$Path = Resolve-Path $Path
if (!$ConfigFile) { $ConfigFile = Join-Path $Path 'korebuild.json' }
if (Test-Path $ConfigFile) {
try {
$config = Get-Content -Raw -Encoding UTF8 -Path $ConfigFile | ConvertFrom-Json
if ($config) {
if (!($Channel) -and (Get-Member -Name 'channel' -InputObject $config)) { [string] $Channel = $config.channel }
if (!($ToolsSource) -and (Get-Member -Name 'toolsSource' -InputObject $config)) { [string] $ToolsSource = $config.toolsSource}
}
}
catch {
Write-Host -ForegroundColor Red $Error[0]
Write-Error "$ConfigFile contains invalid JSON."
exit 1
}
}
if (!$DotNetHome) {
$DotNetHome = if ($env:DOTNET_HOME) { $env:DOTNET_HOME } `
elseif ($env:USERPROFILE) { Join-Path $env:USERPROFILE '.dotnet'} `
elseif ($env:HOME) {Join-Path $env:HOME '.dotnet'}`
else { Join-Path $PSScriptRoot '.dotnet'}
}
if (!$Channel) { $Channel = 'master' }
if (!$ToolsSource) { $ToolsSource = 'https://aspnetcore.blob.core.windows.net/buildtools' }
# Execute
$korebuildPath = Get-KoreBuild
Import-Module -Force -Scope Local (Join-Path $korebuildPath 'KoreBuild.psd1')
try {
Set-KoreBuildSettings -ToolsSource $ToolsSource -DotNetHome $DotNetHome -RepoPath $Path -ConfigFile $ConfigFile -CI:$CI
Invoke-KoreBuildCommand $Command @Arguments
}
finally {
Remove-Module 'KoreBuild' -ErrorAction Ignore
}
================================================
FILE: run.sh
================================================
#!/usr/bin/env bash
set -euo pipefail
#
# variables
#
RESET="\033[0m"
RED="\033[0;31m"
YELLOW="\033[0;33m"
MAGENTA="\033[0;95m"
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
[ -z "${DOTNET_HOME:-}" ] && DOTNET_HOME="$HOME/.dotnet"
verbose=false
update=false
reinstall=false
repo_path="$DIR"
channel=''
tools_source=''
tools_source_suffix=''
ci=false
#
# Functions
#
__usage() {
echo "Usage: $(basename "${BASH_SOURCE[0]}") command [options] [[--] ...]"
echo ""
echo "Arguments:"
echo " command The command to be run."
echo " ... Arguments passed to the command. Variable number of arguments allowed."
echo ""
echo "Options:"
echo " --verbose Show verbose output."
echo " -c|--channel The channel of KoreBuild to download. Overrides the value from the config file.."
echo " --config-file The path to the configuration file that stores values. Defaults to korebuild.json."
echo " -d|--dotnet-home The directory where .NET Core tools will be stored. Defaults to '\$DOTNET_HOME' or '\$HOME/.dotnet."
echo " --path The directory to build. Defaults to the directory containing the script."
echo " -s|--tools-source|-ToolsSource The base url where build tools can be downloaded. Overrides the value from the config file."
echo " --tools-source-suffix|-ToolsSourceSuffix The suffix to append to tools-source. Useful for query strings."
echo " -u|--update Update to the latest KoreBuild even if the lock file is present."
echo " --reinstall Reinstall KoreBuild."
echo " --ci Apply CI specific settings and environment variables."
echo ""
echo "Description:"
echo " This function will create a file \$DIR/korebuild-lock.txt. This lock file can be committed to source, but does not have to be."
echo " When the lockfile is not present, KoreBuild will create one using latest available version from \$channel."
if [[ "${1:-}" != '--no-exit' ]]; then
exit 2
fi
}
get_korebuild() {
local version
local lock_file="$repo_path/korebuild-lock.txt"
if [ ! -f "$lock_file" ] || [ "$update" = true ]; then
__get_remote_file "$tools_source/korebuild/channels/$channel/latest.txt" "$lock_file" "$tools_source_suffix"
fi
version="$(grep 'version:*' -m 1 "$lock_file")"
if [[ "$version" == '' ]]; then
__error "Failed to parse version from $lock_file. Expected a line that begins with 'version:'"
return 1
fi
version="$(echo "${version#version:}" | sed -e 's/^[[:space:]]*//' -e 's/[[:space:]]*$//')"
local korebuild_path="$DOTNET_HOME/buildtools/korebuild/$version"
if [ "$reinstall" = true ] && [ -d "$korebuild_path" ]; then
rm -rf "$korebuild_path"
fi
{
if [ ! -d "$korebuild_path" ]; then
mkdir -p "$korebuild_path"
local remote_path="$tools_source/korebuild/artifacts/$version/korebuild.$version.zip"
tmpfile="$(mktemp)"
echo -e "${MAGENTA}Downloading KoreBuild ${version}${RESET}"
if __get_remote_file "$remote_path" "$tmpfile" "$tools_source_suffix"; then
unzip -q -d "$korebuild_path" "$tmpfile"
fi
rm "$tmpfile" || true
fi
source "$korebuild_path/KoreBuild.sh"
} || {
if [ -d "$korebuild_path" ]; then
echo "Cleaning up after failed installation"
rm -rf "$korebuild_path" || true
fi
return 1
}
}
__error() {
echo -e "${RED}error: $*${RESET}" 1>&2
}
__warn() {
echo -e "${YELLOW}warning: $*${RESET}"
}
__machine_has() {
hash "$1" > /dev/null 2>&1
return $?
}
__get_remote_file() {
local remote_path=$1
local local_path=$2
local remote_path_suffix=$3
if [[ "$remote_path" != 'http'* ]]; then
cp "$remote_path" "$local_path"
return 0
fi
local failed=false
if __machine_has wget; then
wget --tries 10 --quiet -O "$local_path" "${remote_path}${remote_path_suffix}" || failed=true
else
failed=true
fi
if [ "$failed" = true ] && __machine_has curl; then
failed=false
curl --retry 10 -sSL -f --create-dirs -o "$local_path" "${remote_path}${remote_path_suffix}" || failed=true
fi
if [ "$failed" = true ]; then
__error "Download failed: $remote_path" 1>&2
return 1
fi
}
#
# main
#
command="${1:-}"
shift
while [[ $# -gt 0 ]]; do
case $1 in
-\?|-h|--help)
__usage --no-exit
exit 0
;;
-c|--channel|-Channel)
shift
channel="${1:-}"
[ -z "$channel" ] && __usage
;;
--config-file|-ConfigFile)
shift
config_file="${1:-}"
[ -z "$config_file" ] && __usage
if [ ! -f "$config_file" ]; then
__error "Invalid value for --config-file. $config_file does not exist."
exit 1
fi
;;
-d|--dotnet-home|-DotNetHome)
shift
DOTNET_HOME="${1:-}"
[ -z "$DOTNET_HOME" ] && __usage
;;
--path|-Path)
shift
repo_path="${1:-}"
[ -z "$repo_path" ] && __usage
;;
-s|--tools-source|-ToolsSource)
shift
tools_source="${1:-}"
[ -z "$tools_source" ] && __usage
;;
--tools-source-suffix|-ToolsSourceSuffix)
shift
tools_source_suffix="${1:-}"
[ -z "$tools_source_suffix" ] && __usage
;;
-u|--update|-Update)
update=true
;;
--reinstall|-[Rr]einstall)
reinstall=true
;;
--ci|-[Cc][Ii])
ci=true
;;
--verbose|-Verbose)
verbose=true
;;
--)
shift
break
;;
*)
break
;;
esac
shift
done
if ! __machine_has unzip; then
__error 'Missing required command: unzip'
exit 1
fi
if ! __machine_has curl && ! __machine_has wget; then
__error 'Missing required command. Either wget or curl is required.'
exit 1
fi
[ -z "${config_file:-}" ] && config_file="$repo_path/korebuild.json"
if [ -f "$config_file" ]; then
if __machine_has jq ; then
if jq '.' "$config_file" >/dev/null ; then
config_channel="$(jq -r 'select(.channel!=null) | .channel' "$config_file")"
config_tools_source="$(jq -r 'select(.toolsSource!=null) | .toolsSource' "$config_file")"
else
__error "$config_file contains invalid JSON."
exit 1
fi
elif __machine_has python ; then
if python -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'))" >/dev/null ; then
config_channel="$(python -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'));print(obj['channel'] if 'channel' in obj else '')")"
config_tools_source="$(python -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'));print(obj['toolsSource'] if 'toolsSource' in obj else '')")"
else
__error "$config_file contains invalid JSON."
exit 1
fi
elif __machine_has python3 ; then
if python3 -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'))" >/dev/null ; then
config_channel="$(python3 -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'));print(obj['channel'] if 'channel' in obj else '')")"
config_tools_source="$(python3 -c "import json,codecs;obj=json.load(codecs.open('$config_file', 'r', 'utf-8-sig'));print(obj['toolsSource'] if 'toolsSource' in obj else '')")"
else
__error "$config_file contains invalid JSON."
exit 1
fi
else
__error 'Missing required command: jq or python. Could not parse the JSON file.'
exit 1
fi
[ ! -z "${config_channel:-}" ] && channel="$config_channel"
[ ! -z "${config_tools_source:-}" ] && tools_source="$config_tools_source"
fi
[ -z "$channel" ] && channel='master'
[ -z "$tools_source" ] && tools_source='https://aspnetcore.blob.core.windows.net/buildtools'
get_korebuild
set_korebuildsettings "$tools_source" "$DOTNET_HOME" "$repo_path" "$config_file" "$ci"
invoke_korebuild_command "$command" "$@"
================================================
FILE: samples/KeyVaultSample/EnvironmentSecretManager.cs
================================================
using Microsoft.Azure.KeyVault.Models;
using Microsoft.Extensions.Configuration.AzureKeyVault;
namespace ConsoleApplication
{
public class EnvironmentSecretManager : DefaultKeyVaultSecretManager
{
private readonly string _environmentPrefix;
public EnvironmentSecretManager(string environment)
{
_environmentPrefix = environment + "-";
}
public override bool Load(SecretItem secret)
{
return HasEnvironmentPrefix(secret.Identifier.Name);
}
public override string GetKey(SecretBundle secret)
{
var keyName = base.GetKey(secret);
return HasEnvironmentPrefix(keyName)
? keyName.Substring(_environmentPrefix.Length)
: keyName;
}
private bool HasEnvironmentPrefix(string name)
{
return name.StartsWith(_environmentPrefix);
}
}
}
================================================
FILE: samples/KeyVaultSample/KeyVaultSample.csproj
================================================
netcoreapp2.2;net461
portable
Exe
================================================
FILE: samples/KeyVaultSample/Program.cs
================================================
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Cryptography.X509Certificates;
using Microsoft.Extensions.Configuration;
namespace ConsoleApplication
{
public class Program
{
public static void Main(string[] args)
{
var builder = new ConfigurationBuilder();
builder.AddJsonFile("settings.json");
var config = builder.Build();
var store = new X509Store(StoreLocation.CurrentUser);
store.Open(OpenFlags.ReadOnly);
var cert = store.Certificates.Find(X509FindType.FindByThumbprint, config["CertificateThumbprint"], false);
builder.AddAzureKeyVault(
config["Vault"],
config["ClientId"],
cert.OfType().Single(),
new EnvironmentSecretManager("Development"));
store.Close();
config = builder.Build();
Console.WriteLine(config["ConnectionString"]);
}
}
}
================================================
FILE: samples/KeyVaultSample/settings.json
================================================
{
"CertificateThumbprint": "",
"Vault": "",
"ClientId": ""
}
================================================
FILE: src/Config/ChainedBuilderExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// IConfigurationBuilder extension methods for the chaind configuration provider.
///
public static class ChainedBuilderExtensions
{
///
/// Adds an existing configuration to .
///
/// The to add to.
/// The to add.
/// The .
public static IConfigurationBuilder AddConfiguration(this IConfigurationBuilder configurationBuilder, IConfiguration config)
{
if (configurationBuilder == null)
{
throw new ArgumentNullException(nameof(configurationBuilder));
}
if (config == null)
{
throw new ArgumentNullException(nameof(config));
}
configurationBuilder.Add(new ChainedConfigurationSource { Configuration = config });
return configurationBuilder;
}
}
}
================================================
FILE: src/Config/ChainedConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Chained implementation of
///
public class ChainedConfigurationProvider : IConfigurationProvider
{
private readonly IConfiguration _config;
///
/// Initialize a new instance from the source configuration.
///
/// The source configuration.
public ChainedConfigurationProvider(ChainedConfigurationSource source)
{
if (source == null)
{
throw new ArgumentNullException(nameof(source));
}
if (source.Configuration == null)
{
throw new ArgumentNullException(nameof(source.Configuration));
}
_config = source.Configuration;
}
///
/// Tries to get a configuration value for the specified key.
///
/// The key.
/// The value.
/// True if a value for the specified key was found, otherwise false .
public bool TryGet(string key, out string value)
{
value = _config[key];
return !string.IsNullOrEmpty(value);
}
///
/// Sets a configuration value for the specified key.
///
/// The key.
/// The value.
public void Set(string key, string value) => _config[key] = value;
///
/// Returns a change token if this provider supports change tracking, null otherwise.
///
///
public IChangeToken GetReloadToken() => _config.GetReloadToken();
///
/// Loads configuration values from the source represented by this .
///
public void Load() { }
///
/// Returns the immediate descendant configuration keys for a given parent path based on this
/// 's data and the set of keys returned by all the preceding
/// s.
///
/// The child keys returned by the preceding providers for the same parent path.
/// The parent path.
/// The child keys.
public IEnumerable GetChildKeys(
IEnumerable earlierKeys,
string parentPath)
{
var section = parentPath == null ? _config : _config.GetSection(parentPath);
var children = section.GetChildren();
var keys = new List();
keys.AddRange(children.Select(c => c.Key));
return keys.Concat(earlierKeys)
.OrderBy(k => k, ConfigurationKeyComparer.Instance);
}
}
}
================================================
FILE: src/Config/ChainedConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a chained IConfiguration as an .
///
public class ChainedConfigurationSource : IConfigurationSource
{
///
/// The chained configuration.
///
public IConfiguration Configuration { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public IConfigurationProvider Build(IConfigurationBuilder builder)
=> new ChainedConfigurationProvider(this);
}
}
================================================
FILE: src/Config/Config.csproj
================================================
Microsoft.Extensions.Configuration
Microsoft.Extensions.Configuration
Implementation of key-value pair based configuration for Microsoft.Extensions.Configuration. Includes the memory configuration provider.
netstandard2.0
================================================
FILE: src/Config/ConfigurationBuilder.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// Used to build key/value based configuration settings for use in an application.
///
public class ConfigurationBuilder : IConfigurationBuilder
{
///
/// Returns the sources used to obtain configuration values.
///
public IList Sources { get; } = new List();
///
/// Gets a key/value collection that can be used to share data between the
/// and the registered s.
///
public IDictionary Properties { get; } = new Dictionary();
///
/// Adds a new configuration source.
///
/// The configuration source to add.
/// The same .
public IConfigurationBuilder Add(IConfigurationSource source)
{
if (source == null)
{
throw new ArgumentNullException(nameof(source));
}
Sources.Add(source);
return this;
}
///
/// Builds an with keys and values from the set of providers registered in
/// .
///
/// An with keys and values from the registered providers.
public IConfigurationRoot Build()
{
var providers = new List();
foreach (var source in Sources)
{
var provider = source.Build(this);
providers.Add(provider);
}
return new ConfigurationRoot(providers);
}
}
}
================================================
FILE: src/Config/ConfigurationKeyComparer.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// IComparer implementation used to order configuration keys.
///
public class ConfigurationKeyComparer : IComparer
{
private static readonly string[] _keyDelimiterArray = new[] { ConfigurationPath.KeyDelimiter };
///
/// The default instance.
///
public static ConfigurationKeyComparer Instance { get; } = new ConfigurationKeyComparer();
///
/// Compares two strings.
///
/// First string.
/// Second string.
///
public int Compare(string x, string y)
{
var xParts = x?.Split(_keyDelimiterArray, StringSplitOptions.RemoveEmptyEntries) ?? new string[0];
var yParts = y?.Split(_keyDelimiterArray, StringSplitOptions.RemoveEmptyEntries) ?? new string[0];
// Compare each part until we get two parts that are not equal
for (int i = 0; i < Math.Min(xParts.Length, yParts.Length); i++)
{
x = xParts[i];
y = yParts[i];
var value1 = 0;
var value2 = 0;
var xIsInt = x != null && int.TryParse(x, out value1);
var yIsInt = y != null && int.TryParse(y, out value2);
int result = 0;
if (!xIsInt && !yIsInt)
{
// Both are strings
result = string.Compare(x, y, StringComparison.OrdinalIgnoreCase);
}
else if (xIsInt && yIsInt)
{
// Both are int
result = value1 - value2;
}
else
{
// Only one of them is int
result = xIsInt ? -1 : 1;
}
if (result != 0)
{
// One of them is different
return result;
}
}
// If we get here, the common parts are equal.
// If they are of the same length, then they are totally identical
return xParts.Length - yParts.Length;
}
}
}
================================================
FILE: src/Config/ConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Base helper class for implementing an
///
public abstract class ConfigurationProvider : IConfigurationProvider
{
private ConfigurationReloadToken _reloadToken = new ConfigurationReloadToken();
///
/// Initializes a new
///
protected ConfigurationProvider()
{
Data = new Dictionary(StringComparer.OrdinalIgnoreCase);
}
///
/// The configuration key value pairs for this provider.
///
protected IDictionary Data { get; set; }
///
/// Attempts to find a value with the given key, returns true if one is found, false otherwise.
///
/// The key to lookup.
/// The value found at key if one is found.
/// True if key has a value, false otherwise.
public virtual bool TryGet(string key, out string value)
=> Data.TryGetValue(key, out value);
///
/// Sets a value for a given key.
///
/// The configuration key to set.
/// The value to set.
public virtual void Set(string key, string value)
=> Data[key] = value;
///
/// Loads (or reloads) the data for this provider.
///
public virtual void Load()
{ }
///
/// Returns the list of keys that this provider has.
///
/// The earlier keys that other providers contain.
/// The path for the parent IConfiguration.
/// The list of keys for this provider.
public virtual IEnumerable GetChildKeys(
IEnumerable earlierKeys,
string parentPath)
{
var prefix = parentPath == null ? string.Empty : parentPath + ConfigurationPath.KeyDelimiter;
return Data
.Where(kv => kv.Key.StartsWith(prefix, StringComparison.OrdinalIgnoreCase))
.Select(kv => Segment(kv.Key, prefix.Length))
.Concat(earlierKeys)
.OrderBy(k => k, ConfigurationKeyComparer.Instance);
}
private static string Segment(string key, int prefixLength)
{
var indexOf = key.IndexOf(ConfigurationPath.KeyDelimiter, prefixLength, StringComparison.OrdinalIgnoreCase);
return indexOf < 0 ? key.Substring(prefixLength) : key.Substring(prefixLength, indexOf - prefixLength);
}
///
/// Returns a that can be used to listen when this provider is reloaded.
///
///
public IChangeToken GetReloadToken()
{
return _reloadToken;
}
///
/// Triggers the reload change token and creates a new one.
///
protected void OnReload()
{
var previousToken = Interlocked.Exchange(ref _reloadToken, new ConfigurationReloadToken());
previousToken.OnReload();
}
}
}
================================================
FILE: src/Config/ConfigurationReloadToken.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Threading;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Implements
///
public class ConfigurationReloadToken : IChangeToken
{
private CancellationTokenSource _cts = new CancellationTokenSource();
///
/// Indicates if this token will proactively raise callbacks. Callbacks are still guaranteed to be invoked, eventually.
///
public bool ActiveChangeCallbacks => true;
///
/// Gets a value that indicates if a change has occurred.
///
public bool HasChanged => _cts.IsCancellationRequested;
///
/// Registers for a callback that will be invoked when the entry has changed.
/// MUST be set before the callback is invoked.
///
/// The callback to invoke.
/// State to be passed into the callback.
///
public IDisposable RegisterChangeCallback(Action callback, object state) => _cts.Token.Register(callback, state);
///
/// Used to trigger the change token when a reload occurs.
///
public void OnReload() => _cts.Cancel();
}
}
================================================
FILE: src/Config/ConfigurationRoot.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// The root node for a configuration.
///
public class ConfigurationRoot : IConfigurationRoot
{
private IList _providers;
private ConfigurationReloadToken _changeToken = new ConfigurationReloadToken();
///
/// Initializes a Configuration root with a list of providers.
///
/// The s for this configuration.
public ConfigurationRoot(IList providers)
{
if (providers == null)
{
throw new ArgumentNullException(nameof(providers));
}
_providers = providers;
foreach (var p in providers)
{
p.Load();
ChangeToken.OnChange(() => p.GetReloadToken(), () => RaiseChanged());
}
}
///
/// The s for this configuration.
///
public IEnumerable Providers => _providers;
///
/// Gets or sets the value corresponding to a configuration key.
///
/// The configuration key.
/// The configuration value.
public string this[string key]
{
get
{
foreach (var provider in _providers.Reverse())
{
string value;
if (provider.TryGet(key, out value))
{
return value;
}
}
return null;
}
set
{
if (!_providers.Any())
{
throw new InvalidOperationException(Resources.Error_NoSources);
}
foreach (var provider in _providers)
{
provider.Set(key, value);
}
}
}
///
/// Gets the immediate children sub-sections.
///
///
public IEnumerable GetChildren() => GetChildrenImplementation(null);
internal IEnumerable GetChildrenImplementation(string path)
{
return _providers
.Aggregate(Enumerable.Empty(),
(seed, source) => source.GetChildKeys(seed, path))
.Distinct()
.Select(key => GetSection(path == null ? key : ConfigurationPath.Combine(path, key)));
}
///
/// Returns a that can be used to observe when this configuration is reloaded.
///
///
public IChangeToken GetReloadToken() => _changeToken;
///
/// Gets a configuration sub-section with the specified key.
///
/// The key of the configuration section.
/// The .
///
/// This method will never return null . If no matching sub-section is found with the specified key,
/// an empty will be returned.
///
public IConfigurationSection GetSection(string key)
=> new ConfigurationSection(this, key);
///
/// Force the configuration values to be reloaded from the underlying sources.
///
public void Reload()
{
foreach (var provider in _providers)
{
provider.Load();
}
RaiseChanged();
}
private void RaiseChanged()
{
var previousToken = Interlocked.Exchange(ref _changeToken, new ConfigurationReloadToken());
previousToken.OnReload();
}
}
}
================================================
FILE: src/Config/ConfigurationSection.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a section of application configuration values.
///
public class ConfigurationSection : IConfigurationSection
{
private readonly ConfigurationRoot _root;
private readonly string _path;
private string _key;
///
/// Initializes a new instance.
///
/// The configuration root.
/// The path to this section.
public ConfigurationSection(ConfigurationRoot root, string path)
{
if (root == null)
{
throw new ArgumentNullException(nameof(root));
}
if (path == null)
{
throw new ArgumentNullException(nameof(path));
}
_root = root;
_path = path;
}
///
/// Gets the full path to this section from the .
///
public string Path => _path;
///
/// Gets the key this section occupies in its parent.
///
public string Key
{
get
{
if (_key == null)
{
// Key is calculated lazily as last portion of Path
_key = ConfigurationPath.GetSectionKey(_path);
}
return _key;
}
}
///
/// Gets or sets the section value.
///
public string Value
{
get
{
return _root[Path];
}
set
{
_root[Path] = value;
}
}
///
/// Gets or sets the value corresponding to a configuration key.
///
/// The configuration key.
/// The configuration value.
public string this[string key]
{
get
{
return _root[ConfigurationPath.Combine(Path, key)];
}
set
{
_root[ConfigurationPath.Combine(Path, key)] = value;
}
}
///
/// Gets a configuration sub-section with the specified key.
///
/// The key of the configuration section.
/// The .
///
/// This method will never return null . If no matching sub-section is found with the specified key,
/// an empty will be returned.
///
public IConfigurationSection GetSection(string key) => _root.GetSection(ConfigurationPath.Combine(Path, key));
///
/// Gets the immediate descendant configuration sub-sections.
///
/// The configuration sub-sections.
public IEnumerable GetChildren() => _root.GetChildrenImplementation(Path);
///
/// Returns a that can be used to observe when this configuration is reloaded.
///
///
public IChangeToken GetReloadToken() => _root.GetReloadToken();
}
}
================================================
FILE: src/Config/MemoryConfigurationBuilderExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using Microsoft.Extensions.Configuration.Memory;
namespace Microsoft.Extensions.Configuration
{
///
/// IConfigurationBuilder extension methods for the MemoryConfigurationProvider.
///
public static class MemoryConfigurationBuilderExtensions
{
///
/// Adds the memory configuration provider to .
///
/// The to add to.
/// The .
public static IConfigurationBuilder AddInMemoryCollection(this IConfigurationBuilder configurationBuilder)
{
if (configurationBuilder == null)
{
throw new ArgumentNullException(nameof(configurationBuilder));
}
configurationBuilder.Add(new MemoryConfigurationSource());
return configurationBuilder;
}
///
/// Adds the memory configuration provider to .
///
/// The to add to.
/// The data to add to memory configuration provider.
/// The .
public static IConfigurationBuilder AddInMemoryCollection(
this IConfigurationBuilder configurationBuilder,
IEnumerable> initialData)
{
if (configurationBuilder == null)
{
throw new ArgumentNullException(nameof(configurationBuilder));
}
configurationBuilder.Add(new MemoryConfigurationSource { InitialData = initialData });
return configurationBuilder;
}
}
}
================================================
FILE: src/Config/MemoryConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration.Memory
{
///
/// In-memory implementation of
///
public class MemoryConfigurationProvider : ConfigurationProvider, IEnumerable>
{
private readonly MemoryConfigurationSource _source;
///
/// Initialize a new instance from the source.
///
/// The source settings.
public MemoryConfigurationProvider(MemoryConfigurationSource source)
{
if (source == null)
{
throw new ArgumentNullException(nameof(source));
}
_source = source;
if (_source.InitialData != null)
{
foreach (var pair in _source.InitialData)
{
Data.Add(pair.Key, pair.Value);
}
}
}
///
/// Add a new key and value pair.
///
/// The configuration key.
/// The configuration value.
public void Add(string key, string value)
{
Data.Add(key, value);
}
///
/// Returns an enumerator that iterates through the collection.
///
/// An enumerator that can be used to iterate through the collection.
public IEnumerator> GetEnumerator()
{
return Data.GetEnumerator();
}
///
/// Returns an enumerator that iterates through the collection.
///
/// An enumerator that can be used to iterate through the collection.
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
}
================================================
FILE: src/Config/MemoryConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration.Memory
{
///
/// Represents in-memory data as an .
///
public class MemoryConfigurationSource : IConfigurationSource
{
///
/// The initial key value configuration pairs.
///
public IEnumerable> InitialData { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public IConfigurationProvider Build(IConfigurationBuilder builder)
{
return new MemoryConfigurationProvider(this);
}
}
}
================================================
FILE: src/Config/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// A configuration source is not registered. Please register one before setting a value.
///
internal static string Error_NoSources
{
get => GetString("Error_NoSources");
}
///
/// A configuration source is not registered. Please register one before setting a value.
///
internal static string FormatError_NoSources()
=> GetString("Error_NoSources");
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
A configuration source is not registered. Please register one before setting a value.
================================================
FILE: src/Config/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.ChainedBuilderExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddConfiguration",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "config",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ChainedConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationProvider"
],
"Members": [
{
"Kind": "Method",
"Name": "TryGet",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String",
"Direction": "Out"
}
],
"ReturnType": "System.Boolean",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Set",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildKeys",
"Parameters": [
{
"Name": "earlierKeys",
"Type": "System.Collections.Generic.IEnumerable"
},
{
"Name": "parentPath",
"Type": "System.String"
}
],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.ChainedConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ChainedConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Configuration",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Configuration",
"Parameters": [
{
"Name": "value",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationBuilder",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationBuilder"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Sources",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IList",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Properties",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IDictionary",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Add",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.IConfigurationSource"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationRoot",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationKeyComparer",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"System.Collections.Generic.IComparer"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Instance",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.ConfigurationKeyComparer",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Compare",
"Parameters": [
{
"Name": "x",
"Type": "System.String"
},
{
"Name": "y",
"Type": "System.String"
}
],
"ReturnType": "System.Int32",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "System.Collections.Generic.IComparer",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationProvider"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Data",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IDictionary",
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Data",
"Parameters": [
{
"Name": "value",
"Type": "System.Collections.Generic.IDictionary"
}
],
"ReturnType": "System.Void",
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "TryGet",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String",
"Direction": "Out"
}
],
"ReturnType": "System.Boolean",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Set",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildKeys",
"Parameters": [
{
"Name": "earlierKeys",
"Type": "System.Collections.Generic.IEnumerable"
},
{
"Name": "parentPath",
"Type": "System.String"
}
],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "OnReload",
"Parameters": [],
"ReturnType": "System.Void",
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Protected",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationReloadToken",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Primitives.IChangeToken"
],
"Members": [
{
"Kind": "Method",
"Name": "get_ActiveChangeCallbacks",
"Parameters": [],
"ReturnType": "System.Boolean",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Primitives.IChangeToken",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_HasChanged",
"Parameters": [],
"ReturnType": "System.Boolean",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Primitives.IChangeToken",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "RegisterChangeCallback",
"Parameters": [
{
"Name": "callback",
"Type": "System.Action"
},
{
"Name": "state",
"Type": "System.Object"
}
],
"ReturnType": "System.IDisposable",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Primitives.IChangeToken",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "OnReload",
"Parameters": [],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationRoot",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationRoot"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetSection",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildren",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Providers",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationRoot",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Reload",
"Parameters": [],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationRoot",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "providers",
"Type": "System.Collections.Generic.IList"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationSection",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSection"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetSection",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildren",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Path",
"Parameters": [],
"ReturnType": "System.String",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Key",
"Parameters": [],
"ReturnType": "System.String",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Value",
"Parameters": [],
"ReturnType": "System.String",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Value",
"Parameters": [
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "root",
"Type": "Microsoft.Extensions.Configuration.ConfigurationRoot"
},
{
"Name": "path",
"Type": "System.String"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.MemoryConfigurationBuilderExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddInMemoryCollection",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddInMemoryCollection",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "initialData",
"Type": "System.Collections.Generic.IEnumerable>"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Memory.MemoryConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.ConfigurationProvider",
"ImplementedInterfaces": [
"System.Collections.Generic.IEnumerable>"
],
"Members": [
{
"Kind": "Method",
"Name": "Add",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetEnumerator",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerator>",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "System.Collections.Generic.IEnumerable>",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.Memory.MemoryConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Memory.MemoryConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
],
"Members": [
{
"Kind": "Method",
"Name": "get_InitialData",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable>",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_InitialData",
"Parameters": [
{
"Name": "value",
"Type": "System.Collections.Generic.IEnumerable>"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.Abstractions/Config.Abstractions.csproj
================================================
Microsoft.Extensions.Configuration.Abstractions
Microsoft.Extensions.Configuration.Abstractions
Abstractions of key-value pair based configuration.
Commonly used types:
Microsoft.Extensions.Configuration.IConfiguration
Microsoft.Extensions.Configuration.IConfigurationBuilder
Microsoft.Extensions.Configuration.IConfigurationProvider
Microsoft.Extensions.Configuration.IConfigurationRoot
Microsoft.Extensions.Configuration.IConfigurationSection
netstandard2.0
================================================
FILE: src/Config.Abstractions/ConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Linq;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for configuration classes./>.
///
public static class ConfigurationExtensions
{
///
/// Adds a new configuration source.
///
/// The to add to.
/// Configures the source secrets.
/// The .
public static IConfigurationBuilder Add(this IConfigurationBuilder builder, Action configureSource) where TSource : IConfigurationSource, new()
{
var source = new TSource();
configureSource?.Invoke(source);
return builder.Add(source);
}
///
/// Shorthand for GetSection("ConnectionStrings")[name].
///
/// The configuration.
/// The connection string key.
///
public static string GetConnectionString(this IConfiguration configuration, string name)
{
return configuration?.GetSection("ConnectionStrings")?[name];
}
///
/// Get the enumeration of key value pairs within the
///
/// The to enumerate.
/// An enumeration of key value pairs.
public static IEnumerable> AsEnumerable(this IConfiguration configuration) => configuration.AsEnumerable(makePathsRelative: false);
///
/// Get the enumeration of key value pairs within the
///
/// The to enumerate.
/// If true, the child keys returned will have the current configuration's Path trimmed from the front.
/// An enumeration of key value pairs.
public static IEnumerable> AsEnumerable(this IConfiguration configuration, bool makePathsRelative)
{
var stack = new Stack();
stack.Push(configuration);
var rootSection = configuration as IConfigurationSection;
var prefixLength = (makePathsRelative && rootSection != null) ? rootSection.Path.Length + 1 : 0;
while (stack.Count > 0)
{
var config = stack.Pop();
// Don't include the sections value if we are removing paths, since it will be an empty key
if (config is IConfigurationSection section && (!makePathsRelative || config != configuration))
{
yield return new KeyValuePair(section.Path.Substring(prefixLength), section.Value);
}
foreach (var child in config.GetChildren())
{
stack.Push(child);
}
}
}
///
/// Determines whether the section has a or has children
///
public static bool Exists(this IConfigurationSection section)
{
if (section == null)
{
return false;
}
return section.Value != null || section.GetChildren().Any();
}
}
}
================================================
FILE: src/Config.Abstractions/ConfigurationPath.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// Utility methods and constants for manipulating Configuration paths
///
public static class ConfigurationPath
{
///
/// The delimiter ":" used to separate individual keys in a path.
///
public static readonly string KeyDelimiter = ":";
///
/// Combines path segments into one path.
///
/// The path segments to combine.
/// The combined path.
public static string Combine(params string[] pathSegments)
{
if (pathSegments == null)
{
throw new ArgumentNullException(nameof(pathSegments));
}
return string.Join(KeyDelimiter, pathSegments);
}
///
/// Combines path segments into one path.
///
/// The path segments to combine.
/// The combined path.
public static string Combine(IEnumerable pathSegments)
{
if (pathSegments == null)
{
throw new ArgumentNullException(nameof(pathSegments));
}
return string.Join(KeyDelimiter, pathSegments);
}
///
/// Extracts the last path segment from the path.
///
/// The path.
/// The last path segment of the path.
public static string GetSectionKey(string path)
{
if (string.IsNullOrEmpty(path))
{
return path;
}
var lastDelimiterIndex = path.LastIndexOf(KeyDelimiter, StringComparison.OrdinalIgnoreCase);
return lastDelimiterIndex == -1 ? path : path.Substring(lastDelimiterIndex + 1);
}
///
/// Extracts the path corresponding to the parent node for a given path.
///
/// The path.
/// The original path minus the last individual segment found in it. Null if the original path corresponds to a top level node.
public static string GetParentPath(string path)
{
if (string.IsNullOrEmpty(path))
{
return null;
}
var lastDelimiterIndex = path.LastIndexOf(KeyDelimiter, StringComparison.OrdinalIgnoreCase);
return lastDelimiterIndex == -1 ? null : path.Substring(0, lastDelimiterIndex);
}
}
}
================================================
FILE: src/Config.Abstractions/IConfiguration.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a set of key/value application configuration properties.
///
public interface IConfiguration
{
///
/// Gets or sets a configuration value.
///
/// The configuration key.
/// The configuration value.
string this[string key] { get; set; }
///
/// Gets a configuration sub-section with the specified key.
///
/// The key of the configuration section.
/// The .
///
/// This method will never return null . If no matching sub-section is found with the specified key,
/// an empty will be returned.
///
IConfigurationSection GetSection(string key);
///
/// Gets the immediate descendant configuration sub-sections.
///
/// The configuration sub-sections.
IEnumerable GetChildren();
///
/// Returns a that can be used to observe when this configuration is reloaded.
///
/// A .
IChangeToken GetReloadToken();
}
}
================================================
FILE: src/Config.Abstractions/IConfigurationBuilder.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a type used to build application configuration.
///
public interface IConfigurationBuilder
{
///
/// Gets a key/value collection that can be used to share data between the
/// and the registered s.
///
IDictionary Properties { get; }
///
/// Gets the sources used to obtain configuration values
///
IList Sources { get; }
///
/// Adds a new configuration source.
///
/// The configuration source to add.
/// The same .
IConfigurationBuilder Add(IConfigurationSource source);
///
/// Builds an with keys and values from the set of sources registered in
/// .
///
/// An with keys and values from the registered sources.
IConfigurationRoot Build();
}
}
================================================
FILE: src/Config.Abstractions/IConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Provides configuration key/values for an application.
///
public interface IConfigurationProvider
{
///
/// Tries to get a configuration value for the specified key.
///
/// The key.
/// The value.
/// True if a value for the specified key was found, otherwise false .
bool TryGet(string key, out string value);
///
/// Sets a configuration value for the specified key.
///
/// The key.
/// The value.
void Set(string key, string value);
///
/// Returns a change token if this provider supports change tracking, null otherwise.
///
///
IChangeToken GetReloadToken();
///
/// Loads configuration values from the source represented by this .
///
void Load();
///
/// Returns the immediate descendant configuration keys for a given parent path based on this
/// 's data and the set of keys returned by all the preceding
/// s.
///
/// The child keys returned by the preceding providers for the same parent path.
/// The parent path.
/// The child keys.
IEnumerable GetChildKeys(IEnumerable earlierKeys, string parentPath);
}
}
================================================
FILE: src/Config.Abstractions/IConfigurationRoot.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents the root of an hierarchy.
///
public interface IConfigurationRoot : IConfiguration
{
///
/// Force the configuration values to be reloaded from the underlying s.
///
void Reload();
///
/// The s for this configuration.
///
IEnumerable Providers { get; }
}
}
================================================
FILE: src/Config.Abstractions/IConfigurationSection.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a section of application configuration values.
///
public interface IConfigurationSection : IConfiguration
{
///
/// Gets the key this section occupies in its parent.
///
string Key { get; }
///
/// Gets the full path to this section within the .
///
string Path { get; }
///
/// Gets or sets the section value.
///
string Value { get; set; }
}
}
================================================
FILE: src/Config.Abstractions/IConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a source of configuration key/values for an application.
///
public interface IConfigurationSource
{
///
/// Builds the for this source.
///
/// The .
/// An
IConfigurationProvider Build(IConfigurationBuilder builder);
}
}
================================================
FILE: src/Config.Abstractions/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.Abstractions, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Add",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "TSource",
"ParameterPosition": 0,
"New": true,
"BaseTypeOrInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
]
}
]
},
{
"Kind": "Method",
"Name": "GetConnectionString",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "name",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AsEnumerable",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
}
],
"ReturnType": "System.Collections.Generic.IEnumerable>",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AsEnumerable",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "makePathsRelative",
"Type": "System.Boolean"
}
],
"ReturnType": "System.Collections.Generic.IEnumerable>",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Exists",
"Parameters": [
{
"Name": "section",
"Type": "Microsoft.Extensions.Configuration.IConfigurationSection"
}
],
"ReturnType": "System.Boolean",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationPath",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Combine",
"Parameters": [
{
"Name": "pathSegments",
"Type": "System.String[]",
"IsParams": true
}
],
"ReturnType": "System.String",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Combine",
"Parameters": [
{
"Name": "pathSegments",
"Type": "System.Collections.Generic.IEnumerable"
}
],
"ReturnType": "System.String",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetSectionKey",
"Parameters": [
{
"Name": "path",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetParentPath",
"Parameters": [
{
"Name": "path",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Field",
"Name": "KeyDelimiter",
"Parameters": [],
"ReturnType": "System.String",
"Static": true,
"ReadOnly": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfiguration",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "get_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Item",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetSection",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationSection",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildren",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "get_Properties",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IDictionary",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Sources",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IList",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Add",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.IConfigurationSource"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationRoot",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "TryGet",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String",
"Direction": "Out"
}
],
"ReturnType": "System.Boolean",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Set",
"Parameters": [
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetReloadToken",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Primitives.IChangeToken",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetChildKeys",
"Parameters": [
{
"Name": "earlierKeys",
"Type": "System.Collections.Generic.IEnumerable"
},
{
"Name": "parentPath",
"Type": "System.String"
}
],
"ReturnType": "System.Collections.Generic.IEnumerable",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfigurationRoot",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfiguration"
],
"Members": [
{
"Kind": "Method",
"Name": "Reload",
"Parameters": [],
"ReturnType": "System.Void",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Providers",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfigurationSection",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfiguration"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Key",
"Parameters": [],
"ReturnType": "System.String",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Path",
"Parameters": [],
"ReturnType": "System.String",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Value",
"Parameters": [],
"ReturnType": "System.String",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Value",
"Parameters": [
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.AzureKeyVault/AzureKeyVaultConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Security.Cryptography.X509Certificates;
using System.Threading.Tasks;
using Microsoft.Azure.KeyVault;
using Microsoft.Azure.Services.AppAuthentication;
using Microsoft.Extensions.Configuration.AzureKeyVault;
using Microsoft.IdentityModel.Clients.ActiveDirectory;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for registering with .
///
public static class AzureKeyVaultConfigurationExtensions
{
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// The Azure KeyVault uri.
/// The application client id.
/// The client secret to use for authentication.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
string clientId,
string clientSecret)
{
return AddAzureKeyVault(configurationBuilder, vault, clientId, clientSecret, new DefaultKeyVaultSecretManager());
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// The Azure KeyVault uri.
/// The application client id.
/// The client secret to use for authentication.
/// The instance used to control secret loading.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
string clientId,
string clientSecret,
IKeyVaultSecretManager manager)
{
if (clientId == null)
{
throw new ArgumentNullException(nameof(clientId));
}
if (clientSecret == null)
{
throw new ArgumentNullException(nameof(clientSecret));
}
KeyVaultClient.AuthenticationCallback callback =
(authority, resource, scope) => GetTokenFromClientSecret(authority, resource, clientId, clientSecret);
return configurationBuilder.AddAzureKeyVault(vault, new KeyVaultClient(callback), manager);
}
private static async Task GetTokenFromClientSecret(string authority, string resource, string clientId, string clientSecret)
{
var authContext = new AuthenticationContext(authority);
var clientCred = new ClientCredential(clientId, clientSecret);
var result = await authContext.AcquireTokenAsync(resource, clientCred);
return result.AccessToken;
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// Azure KeyVault uri.
/// The application client id.
/// The to use for authentication.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
string clientId,
X509Certificate2 certificate)
{
return AddAzureKeyVault(configurationBuilder, vault, clientId, certificate, new DefaultKeyVaultSecretManager());
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// Azure KeyVault uri.
/// The application client id.
/// The to use for authentication.
/// The instance used to control secret loading.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
string clientId,
X509Certificate2 certificate,
IKeyVaultSecretManager manager)
{
if (clientId == null)
{
throw new ArgumentNullException(nameof(clientId));
}
if (certificate == null)
{
throw new ArgumentNullException(nameof(certificate));
}
KeyVaultClient.AuthenticationCallback callback =
(authority, resource, scope) => GetTokenFromClientCertificate(authority, resource, clientId, certificate);
return configurationBuilder.AddAzureKeyVault(vault, new KeyVaultClient(callback), manager);
}
private static async Task GetTokenFromClientCertificate(string authority, string resource, string clientId, X509Certificate2 certificate)
{
var authContext = new AuthenticationContext(authority);
var result = await authContext.AcquireTokenAsync(resource, new ClientAssertionCertificate(clientId, certificate));
return result.AccessToken;
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// Azure KeyVault uri.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault)
{
return AddAzureKeyVault(configurationBuilder, vault, new DefaultKeyVaultSecretManager());
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// Azure KeyVault uri.
/// The instance used to control secret loading.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
IKeyVaultSecretManager manager)
{
var azureServiceTokenProvider = new AzureServiceTokenProvider();
var authenticationCallback = new KeyVaultClient.AuthenticationCallback(azureServiceTokenProvider.KeyVaultTokenCallback);
var keyVaultClient = new KeyVaultClient(authenticationCallback);
return AddAzureKeyVault(configurationBuilder, vault, keyVaultClient, manager);
}
///
/// Adds an that reads configuration values from the Azure KeyVault.
///
/// The to add to.
/// Azure KeyVault uri.
/// The to use for retrieving values.
/// The instance used to control secret loading.
/// The .
public static IConfigurationBuilder AddAzureKeyVault(
this IConfigurationBuilder configurationBuilder,
string vault,
KeyVaultClient client,
IKeyVaultSecretManager manager)
{
if (configurationBuilder == null)
{
throw new ArgumentNullException(nameof(configurationBuilder));
}
if (client == null)
{
throw new ArgumentNullException(nameof(client));
}
if (vault == null)
{
throw new ArgumentNullException(nameof(vault));
}
if (manager == null)
{
throw new ArgumentNullException(nameof(manager));
}
configurationBuilder.Add(new AzureKeyVaultConfigurationSource()
{
Client = client,
Vault = vault,
Manager = manager
});
return configurationBuilder;
}
}
}
================================================
FILE: src/Config.AzureKeyVault/AzureKeyVaultConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.Azure.KeyVault;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
/// An AzureKeyVault based .
///
internal class AzureKeyVaultConfigurationProvider : ConfigurationProvider
{
private readonly IKeyVaultClient _client;
private readonly string _vault;
private readonly IKeyVaultSecretManager _manager;
///
/// Creates a new instance of .
///
/// The to use for retrieving values.
/// Azure KeyVault uri.
///
public AzureKeyVaultConfigurationProvider(IKeyVaultClient client, string vault, IKeyVaultSecretManager manager)
{
if (client == null)
{
throw new ArgumentNullException(nameof(client));
}
if (vault == null)
{
throw new ArgumentNullException(nameof(vault));
}
if (manager == null)
{
throw new ArgumentNullException(nameof(manager));
}
_client = client;
_vault = vault;
_manager = manager;
}
public override void Load() => LoadAsync().ConfigureAwait(false).GetAwaiter().GetResult();
private async Task LoadAsync()
{
var data = new Dictionary(StringComparer.OrdinalIgnoreCase);
var secrets = await _client.GetSecretsAsync(_vault).ConfigureAwait(false);
do
{
foreach (var secretItem in secrets)
{
if (!_manager.Load(secretItem) || (secretItem.Attributes?.Enabled != true))
{
continue;
}
var value = await _client.GetSecretAsync(secretItem.Id).ConfigureAwait(false);
var key = _manager.GetKey(value);
data.Add(key, value.Value);
}
secrets = secrets.NextPageLink != null ?
await _client.GetSecretsNextAsync(secrets.NextPageLink).ConfigureAwait(false) :
null;
} while (secrets != null);
Data = data;
}
}
}
================================================
FILE: src/Config.AzureKeyVault/AzureKeyVaultConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.Azure.KeyVault;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
/// Represents Azure KeyVault secrets as an .
///
internal class AzureKeyVaultConfigurationSource : IConfigurationSource
{
///
/// Gets or sets the to use for retrieving values.
///
public KeyVaultClient Client { get; set; }
///
/// Gets or sets the vault uri.
///
public string Vault { get; set; }
///
/// Gets or sets the instance used to control secret loading.
///
public IKeyVaultSecretManager Manager { get; set; }
///
public IConfigurationProvider Build(IConfigurationBuilder builder)
{
return new AzureKeyVaultConfigurationProvider(new KeyVaultClientWrapper(Client), Vault, Manager);
}
}
}
================================================
FILE: src/Config.AzureKeyVault/Config.AzureKeyVault.csproj
================================================
Microsoft.Extensions.Configuration.AzureKeyVault
Microsoft.Extensions.Configuration.AzureKeyVault
Azure KeyVault configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);azure;keyvault
================================================
FILE: src/Config.AzureKeyVault/DefaultKeyVaultSecretManager.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.Azure.KeyVault;
using Microsoft.Azure.KeyVault.Models;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
/// Default implementation of that loads all secrets
/// and replaces '--' with ':" in key names.
///
public class DefaultKeyVaultSecretManager : IKeyVaultSecretManager
{
///
public virtual string GetKey(SecretBundle secret)
{
return secret.SecretIdentifier.Name.Replace("--", ConfigurationPath.KeyDelimiter);
}
///
public virtual bool Load(SecretItem secret)
{
return true;
}
}
}
================================================
FILE: src/Config.AzureKeyVault/IKeyVaultClient.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Threading.Tasks;
using Microsoft.Azure.KeyVault;
using Microsoft.Azure.KeyVault.Models;
using Microsoft.Rest.Azure;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
/// Client class to perform cryptographic key operations and vault operations
/// against the Key Vault service.
/// Thread safety: This class is thread-safe.
///
internal interface IKeyVaultClient
{
/// List secrets in the specified vault
/// The URL for the vault containing the secrets.
/// A response message containing a list of secrets in the vault along with a link to the next page of secrets
Task> GetSecretsAsync(string vault);
/// Gets a secret.
/// The URL for the secret.
/// A response message containing the secret
Task GetSecretAsync(string secretIdentifier);
/// List the next page of secrets
/// nextLink value from a previous call to GetSecrets or GetSecretsNext
/// A response message containing a list of secrets in the vault along with a link to the next page of secrets
Task> GetSecretsNextAsync(string nextLink);
}
}
================================================
FILE: src/Config.AzureKeyVault/IKeyVaultSecretManager.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.Azure.KeyVault.Models;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
/// The instance used to control secret loading.
///
public interface IKeyVaultSecretManager
{
///
/// Checks if value should be retrieved.
///
/// The instance.
/// true is secrets value should be loaded, otherwise false.
bool Load(SecretItem secret);
///
/// Maps secret to a configuration key.
///
/// The instance.
/// Configuration key name to store secret value.
string GetKey(SecretBundle secret);
}
}
================================================
FILE: src/Config.AzureKeyVault/KeyVaultClientWrapper.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Threading.Tasks;
using Microsoft.Azure.KeyVault;
using Microsoft.Azure.KeyVault.Models;
using Microsoft.Rest.Azure;
namespace Microsoft.Extensions.Configuration.AzureKeyVault
{
///
internal class KeyVaultClientWrapper : IKeyVaultClient
{
private readonly KeyVaultClient _keyVaultClientImplementation;
///
/// Creates a new instance of .
///
/// The instance to wrap.
public KeyVaultClientWrapper(KeyVaultClient keyVaultClientImplementation)
{
_keyVaultClientImplementation = keyVaultClientImplementation;
}
///
public Task> GetSecretsAsync(string vault)
{
return _keyVaultClientImplementation.GetSecretsAsync(vault);
}
///
public Task GetSecretAsync(string secretIdentifier)
{
return _keyVaultClientImplementation.GetSecretAsync(secretIdentifier);
}
///
public Task> GetSecretsNextAsync(string nextLink)
{
return _keyVaultClientImplementation.GetSecretsNextAsync(nextLink);
}
}
}
================================================
FILE: src/Config.AzureKeyVault/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.AzureKeyVault.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")]
================================================
FILE: src/Config.AzureKeyVault/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.AzureKeyVault, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.AzureKeyVaultConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "clientId",
"Type": "System.String"
},
{
"Name": "clientSecret",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "clientId",
"Type": "System.String"
},
{
"Name": "clientSecret",
"Type": "System.String"
},
{
"Name": "manager",
"Type": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "clientId",
"Type": "System.String"
},
{
"Name": "certificate",
"Type": "System.Security.Cryptography.X509Certificates.X509Certificate2"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "clientId",
"Type": "System.String"
},
{
"Name": "certificate",
"Type": "System.Security.Cryptography.X509Certificates.X509Certificate2"
},
{
"Name": "manager",
"Type": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "manager",
"Type": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddAzureKeyVault",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "vault",
"Type": "System.String"
},
{
"Name": "client",
"Type": "Microsoft.Azure.KeyVault.KeyVaultClient"
},
{
"Name": "manager",
"Type": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.AzureKeyVault.DefaultKeyVaultSecretManager",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager"
],
"Members": [
{
"Kind": "Method",
"Name": "GetKey",
"Parameters": [
{
"Name": "secret",
"Type": "Microsoft.Azure.KeyVault.Models.SecretBundle"
}
],
"ReturnType": "System.String",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "secret",
"Type": "Microsoft.Azure.KeyVault.Models.SecretItem"
}
],
"ReturnType": "System.Boolean",
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.AzureKeyVault.IKeyVaultSecretManager",
"Visibility": "Public",
"Kind": "Interface",
"Abstract": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "secret",
"Type": "Microsoft.Azure.KeyVault.Models.SecretItem"
}
],
"ReturnType": "System.Boolean",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetKey",
"Parameters": [
{
"Name": "secret",
"Type": "Microsoft.Azure.KeyVault.Models.SecretBundle"
}
],
"ReturnType": "System.String",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.Binder/BinderOptions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration
{
///
/// Options class used by the .
///
public class BinderOptions
{
///
/// When false (the default), the binder will only attempt to set public properties.
/// If true, the binder will attempt to set all non read-only properties.
///
public bool BindNonPublicProperties { get; set; }
}
}
================================================
FILE: src/Config.Binder/Config.Binder.csproj
================================================
Microsoft.Extensions.Configuration.Binder
Microsoft.Extensions.Configuration.Binder
Functionality to bind an object to data in configuration providers for Microsoft.Extensions.Configuration.
netstandard2.0
================================================
FILE: src/Config.Binder/ConfigurationBinder.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Reflection;
using Microsoft.Extensions.Configuration.Binder;
namespace Microsoft.Extensions.Configuration
{
///
/// Static helper class that allows binding strongly typed objects to configuration values.
///
public static class ConfigurationBinder
{
///
/// Attempts to bind the configuration instance to a new instance of type T.
/// If this configuration section has a value, that will be used.
/// Otherwise binding by matching property names against configuration keys recursively.
///
/// The type of the new instance to bind.
/// The configuration instance to bind.
/// The new instance of T if successful, default(T) otherwise.
public static T Get(this IConfiguration configuration)
=> configuration.Get(_ => { });
///
/// Attempts to bind the configuration instance to a new instance of type T.
/// If this configuration section has a value, that will be used.
/// Otherwise binding by matching property names against configuration keys recursively.
///
/// The type of the new instance to bind.
/// The configuration instance to bind.
/// Configures the binder options.
/// The new instance of T if successful, default(T) otherwise.
public static T Get(this IConfiguration configuration, Action configureOptions)
{
if (configuration == null)
{
throw new ArgumentNullException(nameof(configuration));
}
var result = configuration.Get(typeof(T), configureOptions);
if (result == null)
{
return default(T);
}
return (T)result;
}
///
/// Attempts to bind the configuration instance to a new instance of type T.
/// If this configuration section has a value, that will be used.
/// Otherwise binding by matching property names against configuration keys recursively.
///
/// The configuration instance to bind.
/// The type of the new instance to bind.
/// The new instance if successful, null otherwise.
public static object Get(this IConfiguration configuration, Type type)
=> configuration.Get(type, _ => { });
///
/// Attempts to bind the configuration instance to a new instance of type T.
/// If this configuration section has a value, that will be used.
/// Otherwise binding by matching property names against configuration keys recursively.
///
/// The configuration instance to bind.
/// The type of the new instance to bind.
/// Configures the binder options.
/// The new instance if successful, null otherwise.
public static object Get(this IConfiguration configuration, Type type, Action configureOptions)
{
if (configuration == null)
{
throw new ArgumentNullException(nameof(configuration));
}
var options = new BinderOptions();
configureOptions?.Invoke(options);
return BindInstance(type, instance: null, config: configuration, options: options);
}
///
/// Attempts to bind the given object instance to the configuration section specified by the key by matching property names against configuration keys recursively.
///
/// The configuration instance to bind.
/// The key of the configuration section to bind.
/// The object to bind.
public static void Bind(this IConfiguration configuration, string key, object instance)
=> configuration.GetSection(key).Bind(instance);
///
/// Attempts to bind the given object instance to configuration values by matching property names against configuration keys recursively.
///
/// The configuration instance to bind.
/// The object to bind.
public static void Bind(this IConfiguration configuration, object instance)
=> configuration.Bind(instance, o => { });
///
/// Attempts to bind the given object instance to configuration values by matching property names against configuration keys recursively.
///
/// The configuration instance to bind.
/// The object to bind.
/// Configures the binder options.
public static void Bind(this IConfiguration configuration, object instance, Action configureOptions)
{
if (configuration == null)
{
throw new ArgumentNullException(nameof(configuration));
}
if (instance != null)
{
var options = new BinderOptions();
configureOptions?.Invoke(options);
BindInstance(instance.GetType(), instance, configuration, options);
}
}
///
/// Extracts the value with the specified key and converts it to type T.
///
/// The type to convert the value to.
/// The configuration.
/// The key of the configuration section's value to convert.
/// The converted value.
public static T GetValue(this IConfiguration configuration, string key)
{
return GetValue(configuration, key, default(T));
}
///
/// Extracts the value with the specified key and converts it to type T.
///
/// The type to convert the value to.
/// The configuration.
/// The key of the configuration section's value to convert.
/// The default value to use if no value is found.
/// The converted value.
public static T GetValue(this IConfiguration configuration, string key, T defaultValue)
{
return (T)GetValue(configuration, typeof(T), key, defaultValue);
}
///
/// Extracts the value with the specified key and converts it to the specified type.
///
/// The configuration.
/// The type to convert the value to.
/// The key of the configuration section's value to convert.
/// The converted value.
public static object GetValue(this IConfiguration configuration, Type type, string key)
{
return GetValue(configuration, type, key, defaultValue: null);
}
///
/// Extracts the value with the specified key and converts it to the specified type.
///
/// The configuration.
/// The type to convert the value to.
/// The key of the configuration section's value to convert.
/// The default value to use if no value is found.
/// The converted value.
public static object GetValue(this IConfiguration configuration, Type type, string key, object defaultValue)
{
var value = configuration.GetSection(key).Value;
if (value != null)
{
return ConvertValue(type, value);
}
return defaultValue;
}
private static void BindNonScalar(this IConfiguration configuration, object instance, BinderOptions options)
{
if (instance != null)
{
foreach (var property in GetAllProperties(instance.GetType().GetTypeInfo()))
{
BindProperty(property, instance, configuration, options);
}
}
}
private static void BindProperty(PropertyInfo property, object instance, IConfiguration config, BinderOptions options)
{
// We don't support set only, non public, or indexer properties
if (property.GetMethod == null ||
(!options.BindNonPublicProperties && !property.GetMethod.IsPublic) ||
property.GetMethod.GetParameters().Length > 0)
{
return;
}
var propertyValue = property.GetValue(instance);
var hasSetter = property.SetMethod != null && (property.SetMethod.IsPublic || options.BindNonPublicProperties);
if (propertyValue == null && !hasSetter)
{
// Property doesn't have a value and we cannot set it so there is no
// point in going further down the graph
return;
}
propertyValue = BindInstance(property.PropertyType, propertyValue, config.GetSection(property.Name), options);
if (propertyValue != null && hasSetter)
{
property.SetValue(instance, propertyValue);
}
}
private static object BindToCollection(TypeInfo typeInfo, IConfiguration config, BinderOptions options)
{
var type = typeof(List<>).MakeGenericType(typeInfo.GenericTypeArguments[0]);
var instance = Activator.CreateInstance(type);
BindCollection(instance, type, config, options);
return instance;
}
// Try to create an array/dictionary instance to back various collection interfaces
private static object AttemptBindToCollectionInterfaces(Type type, IConfiguration config, BinderOptions options)
{
var typeInfo = type.GetTypeInfo();
if (!typeInfo.IsInterface)
{
return null;
}
var collectionInterface = FindOpenGenericInterface(typeof(IReadOnlyList<>), type);
if (collectionInterface != null)
{
// IEnumerable is guaranteed to have exactly one parameter
return BindToCollection(typeInfo, config, options);
}
collectionInterface = FindOpenGenericInterface(typeof(IReadOnlyDictionary<,>), type);
if (collectionInterface != null)
{
var dictionaryType = typeof(Dictionary<,>).MakeGenericType(typeInfo.GenericTypeArguments[0], typeInfo.GenericTypeArguments[1]);
var instance = Activator.CreateInstance(dictionaryType);
BindDictionary(instance, dictionaryType, config, options);
return instance;
}
collectionInterface = FindOpenGenericInterface(typeof(IDictionary<,>), type);
if (collectionInterface != null)
{
var instance = Activator.CreateInstance(typeof(Dictionary<,>).MakeGenericType(typeInfo.GenericTypeArguments[0], typeInfo.GenericTypeArguments[1]));
BindDictionary(instance, collectionInterface, config, options);
return instance;
}
collectionInterface = FindOpenGenericInterface(typeof(IReadOnlyCollection<>), type);
if (collectionInterface != null)
{
// IReadOnlyCollection is guaranteed to have exactly one parameter
return BindToCollection(typeInfo, config, options);
}
collectionInterface = FindOpenGenericInterface(typeof(ICollection<>), type);
if (collectionInterface != null)
{
// ICollection is guaranteed to have exactly one parameter
return BindToCollection(typeInfo, config, options);
}
collectionInterface = FindOpenGenericInterface(typeof(IEnumerable<>), type);
if (collectionInterface != null)
{
// IEnumerable is guaranteed to have exactly one parameter
return BindToCollection(typeInfo, config, options);
}
return null;
}
private static object BindInstance(Type type, object instance, IConfiguration config, BinderOptions options)
{
// if binding IConfigurationSection, break early
if (type == typeof(IConfigurationSection))
{
return config;
}
var section = config as IConfigurationSection;
var configValue = section?.Value;
object convertedValue;
Exception error;
if (configValue != null && TryConvertValue(type, configValue, out convertedValue, out error))
{
if (error != null)
{
throw error;
}
// Leaf nodes are always reinitialized
return convertedValue;
}
if (config != null && config.GetChildren().Any())
{
// If we don't have an instance, try to create one
if (instance == null)
{
// We are alrady done if binding to a new collection instance worked
instance = AttemptBindToCollectionInterfaces(type, config, options);
if (instance != null)
{
return instance;
}
instance = CreateInstance(type);
}
// See if its a Dictionary
var collectionInterface = FindOpenGenericInterface(typeof(IDictionary<,>), type);
if (collectionInterface != null)
{
BindDictionary(instance, collectionInterface, config, options);
}
else if (type.IsArray)
{
instance = BindArray((Array)instance, config, options);
}
else
{
// See if its an ICollection
collectionInterface = FindOpenGenericInterface(typeof(ICollection<>), type);
if (collectionInterface != null)
{
BindCollection(instance, collectionInterface, config, options);
}
// Something else
else
{
BindNonScalar(config, instance, options);
}
}
}
return instance;
}
private static object CreateInstance(Type type)
{
var typeInfo = type.GetTypeInfo();
if (typeInfo.IsInterface || typeInfo.IsAbstract)
{
throw new InvalidOperationException(Resources.FormatError_CannotActivateAbstractOrInterface(type));
}
if (type.IsArray)
{
if (typeInfo.GetArrayRank() > 1)
{
throw new InvalidOperationException(Resources.FormatError_UnsupportedMultidimensionalArray(type));
}
return Array.CreateInstance(typeInfo.GetElementType(), 0);
}
var hasDefaultConstructor = typeInfo.DeclaredConstructors.Any(ctor => ctor.IsPublic && ctor.GetParameters().Length == 0);
if (!hasDefaultConstructor)
{
throw new InvalidOperationException(Resources.FormatError_MissingParameterlessConstructor(type));
}
try
{
return Activator.CreateInstance(type);
}
catch (Exception ex)
{
throw new InvalidOperationException(Resources.FormatError_FailedToActivate(type), ex);
}
}
private static void BindDictionary(object dictionary, Type dictionaryType, IConfiguration config, BinderOptions options)
{
var typeInfo = dictionaryType.GetTypeInfo();
// IDictionary is guaranteed to have exactly two parameters
var keyType = typeInfo.GenericTypeArguments[0];
var valueType = typeInfo.GenericTypeArguments[1];
var keyTypeIsEnum = keyType.GetTypeInfo().IsEnum;
if (keyType != typeof(string) && !keyTypeIsEnum)
{
// We only support string and enum keys
return;
}
var setter = typeInfo.GetDeclaredProperty("Item");
foreach (var child in config.GetChildren())
{
var item = BindInstance(
type: valueType,
instance: null,
config: child,
options: options);
if (item != null)
{
if (keyType == typeof(string))
{
var key = child.Key;
setter.SetValue(dictionary, item, new object[] { key });
}
else if (keyTypeIsEnum)
{
var key = Convert.ToInt32(Enum.Parse(keyType, child.Key));
setter.SetValue(dictionary, item, new object[] { key });
}
}
}
}
private static void BindCollection(object collection, Type collectionType, IConfiguration config, BinderOptions options)
{
var typeInfo = collectionType.GetTypeInfo();
// ICollection is guaranteed to have exactly one parameter
var itemType = typeInfo.GenericTypeArguments[0];
var addMethod = typeInfo.GetDeclaredMethod("Add");
foreach (var section in config.GetChildren())
{
try
{
var item = BindInstance(
type: itemType,
instance: null,
config: section,
options: options);
if (item != null)
{
addMethod.Invoke(collection, new[] { item });
}
}
catch
{
}
}
}
private static Array BindArray(Array source, IConfiguration config, BinderOptions options)
{
var children = config.GetChildren().ToArray();
var arrayLength = source.Length;
var elementType = source.GetType().GetElementType();
var newArray = Array.CreateInstance(elementType, arrayLength + children.Length);
// binding to array has to preserve already initialized arrays with values
if (arrayLength > 0)
{
Array.Copy(source, newArray, arrayLength);
}
for (int i = 0; i < children.Length; i++)
{
try
{
var item = BindInstance(
type: elementType,
instance: null,
config: children[i],
options: options);
if (item != null)
{
newArray.SetValue(item, arrayLength + i);
}
}
catch
{
}
}
return newArray;
}
private static bool TryConvertValue(Type type, string value, out object result, out Exception error)
{
error = null;
result = null;
if (type == typeof(object))
{
result = value;
return true;
}
if (type.GetTypeInfo().IsGenericType && type.GetGenericTypeDefinition() == typeof(Nullable<>))
{
if (string.IsNullOrEmpty(value))
{
return true;
}
return TryConvertValue(Nullable.GetUnderlyingType(type), value, out result, out error);
}
var converter = TypeDescriptor.GetConverter(type);
if (converter.CanConvertFrom(typeof(string)))
{
try
{
result = converter.ConvertFromInvariantString(value);
}
catch (Exception ex)
{
error = new InvalidOperationException(Resources.FormatError_FailedBinding(value, type), ex);
}
return true;
}
return false;
}
private static object ConvertValue(Type type, string value)
{
object result;
Exception error;
TryConvertValue(type, value, out result, out error);
if (error != null)
{
throw error;
}
return result;
}
private static Type FindOpenGenericInterface(Type expected, Type actual)
{
var actualTypeInfo = actual.GetTypeInfo();
if(actualTypeInfo.IsGenericType &&
actual.GetGenericTypeDefinition() == expected)
{
return actual;
}
var interfaces = actualTypeInfo.ImplementedInterfaces;
foreach (var interfaceType in interfaces)
{
if (interfaceType.GetTypeInfo().IsGenericType &&
interfaceType.GetGenericTypeDefinition() == expected)
{
return interfaceType;
}
}
return null;
}
private static IEnumerable GetAllProperties(TypeInfo type)
{
var allProperties = new List();
do
{
allProperties.AddRange(type.DeclaredProperties);
type = type.BaseType.GetTypeInfo();
}
while (type != typeof(object).GetTypeInfo());
return allProperties;
}
}
}
================================================
FILE: src/Config.Binder/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.Binder.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.Binder/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.Binder
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.Binder.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// Cannot create instance of type '{0}' because it is either abstract or an interface.
///
internal static string Error_CannotActivateAbstractOrInterface
{
get => GetString("Error_CannotActivateAbstractOrInterface");
}
///
/// Cannot create instance of type '{0}' because it is either abstract or an interface.
///
internal static string FormatError_CannotActivateAbstractOrInterface(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_CannotActivateAbstractOrInterface"), p0);
///
/// Failed to convert '{0}' to type '{1}'.
///
internal static string Error_FailedBinding
{
get => GetString("Error_FailedBinding");
}
///
/// Failed to convert '{0}' to type '{1}'.
///
internal static string FormatError_FailedBinding(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_FailedBinding"), p0, p1);
///
/// Failed to create instance of type '{0}'.
///
internal static string Error_FailedToActivate
{
get => GetString("Error_FailedToActivate");
}
///
/// Failed to create instance of type '{0}'.
///
internal static string FormatError_FailedToActivate(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_FailedToActivate"), p0);
///
/// Cannot create instance of type '{0}' because it is missing a public parameterless constructor.
///
internal static string Error_MissingParameterlessConstructor
{
get => GetString("Error_MissingParameterlessConstructor");
}
///
/// Cannot create instance of type '{0}' because it is missing a public parameterless constructor.
///
internal static string FormatError_MissingParameterlessConstructor(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_MissingParameterlessConstructor"), p0);
///
/// Cannot create instance of type '{0}' because multidimensional arrays are not supported.
///
internal static string Error_UnsupportedMultidimensionalArray
{
get => GetString("Error_UnsupportedMultidimensionalArray");
}
///
/// Cannot create instance of type '{0}' because multidimensional arrays are not supported.
///
internal static string FormatError_UnsupportedMultidimensionalArray(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_UnsupportedMultidimensionalArray"), p0);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.Binder/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Cannot create instance of type '{0}' because it is either abstract or an interface.
Failed to convert '{0}' to type '{1}'.
Failed to create instance of type '{0}'.
Cannot create instance of type '{0}' because it is missing a public parameterless constructor.
Cannot create instance of type '{0}' because multidimensional arrays are not supported.
================================================
FILE: src/Config.Binder/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.Binder, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.BinderOptions",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "get_BindNonPublicProperties",
"Parameters": [],
"ReturnType": "System.Boolean",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_BindNonPublicProperties",
"Parameters": [
{
"Name": "value",
"Type": "System.Boolean"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.ConfigurationBinder",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Get",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
}
],
"ReturnType": "T0",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "Get",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "configureOptions",
"Type": "System.Action"
}
],
"ReturnType": "T0",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "Get",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "type",
"Type": "System.Type"
}
],
"ReturnType": "System.Object",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Get",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "type",
"Type": "System.Type"
},
{
"Name": "configureOptions",
"Type": "System.Action"
}
],
"ReturnType": "System.Object",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Bind",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "instance",
"Type": "System.Object"
}
],
"ReturnType": "System.Void",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Bind",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "instance",
"Type": "System.Object"
}
],
"ReturnType": "System.Void",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Bind",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "instance",
"Type": "System.Object"
},
{
"Name": "configureOptions",
"Type": "System.Action"
}
],
"ReturnType": "System.Void",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetValue",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "T0",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "GetValue",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "defaultValue",
"Type": "T0"
}
],
"ReturnType": "T0",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "GetValue",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "type",
"Type": "System.Type"
},
{
"Name": "key",
"Type": "System.String"
}
],
"ReturnType": "System.Object",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetValue",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfiguration"
},
{
"Name": "type",
"Type": "System.Type"
},
{
"Name": "key",
"Type": "System.String"
},
{
"Name": "defaultValue",
"Type": "System.Object"
}
],
"ReturnType": "System.Object",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.CommandLine/CommandLineConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using Microsoft.Extensions.Configuration.CommandLine;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for registering with .
///
public static class CommandLineConfigurationExtensions
{
///
/// Adds an that reads configuration values from the command line.
///
/// The to add to.
/// The command line args.
/// The .
public static IConfigurationBuilder AddCommandLine(this IConfigurationBuilder configurationBuilder, string[] args)
{
return configurationBuilder.AddCommandLine(args, switchMappings: null);
}
///
/// Adds an that reads configuration values from the command line using the specified switch mappings.
///
/// The to add to.
/// The command line args.
/// The switch mappings.
/// The .
public static IConfigurationBuilder AddCommandLine(
this IConfigurationBuilder configurationBuilder,
string[] args,
IDictionary switchMappings)
{
configurationBuilder.Add(new CommandLineConfigurationSource { Args = args, SwitchMappings = switchMappings });
return configurationBuilder;
}
///
/// Adds an that reads configuration values from the command line.
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddCommandLine(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.CommandLine/CommandLineConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration.CommandLine
{
///
/// A command line based .
///
public class CommandLineConfigurationProvider : ConfigurationProvider
{
private readonly Dictionary _switchMappings;
///
/// Initializes a new instance.
///
/// The command line args.
/// The switch mappings.
public CommandLineConfigurationProvider(IEnumerable args, IDictionary switchMappings = null)
{
Args = args ?? throw new ArgumentNullException(nameof(args));
if (switchMappings != null)
{
_switchMappings = GetValidatedSwitchMappingsCopy(switchMappings);
}
}
///
/// The command line arguments.
///
protected IEnumerable Args { get; private set; }
///
/// Loads the configuration data from the command line args.
///
public override void Load()
{
var data = new Dictionary(StringComparer.OrdinalIgnoreCase);
string key, value;
using (var enumerator = Args.GetEnumerator())
{
while (enumerator.MoveNext())
{
var currentArg = enumerator.Current;
var keyStartIndex = 0;
if (currentArg.StartsWith("--"))
{
keyStartIndex = 2;
}
else if (currentArg.StartsWith("-"))
{
keyStartIndex = 1;
}
else if (currentArg.StartsWith("/"))
{
// "/SomeSwitch" is equivalent to "--SomeSwitch" when interpreting switch mappings
// So we do a conversion to simplify later processing
currentArg = string.Format("--{0}", currentArg.Substring(1));
keyStartIndex = 2;
}
var separator = currentArg.IndexOf('=');
if (separator < 0)
{
// If there is neither equal sign nor prefix in current arugment, it is an invalid format
if (keyStartIndex == 0)
{
// Ignore invalid formats
continue;
}
// If the switch is a key in given switch mappings, interpret it
if (_switchMappings != null && _switchMappings.ContainsKey(currentArg))
{
key = _switchMappings[currentArg];
}
// If the switch starts with a single "-" and it isn't in given mappings , it is an invalid usage so ignore it
else if (keyStartIndex == 1)
{
continue;
}
// Otherwise, use the switch name directly as a key
else
{
key = currentArg.Substring(keyStartIndex);
}
var previousKey = enumerator.Current;
if (!enumerator.MoveNext())
{
// ignore missing values
continue;
}
value = enumerator.Current;
}
else
{
var keySegment = currentArg.Substring(0, separator);
// If the switch is a key in given switch mappings, interpret it
if (_switchMappings != null && _switchMappings.ContainsKey(keySegment))
{
key = _switchMappings[keySegment];
}
// If the switch starts with a single "-" and it isn't in given mappings , it is an invalid usage
else if (keyStartIndex == 1)
{
throw new FormatException(Resources.FormatError_ShortSwitchNotDefined(currentArg));
}
// Otherwise, use the switch name directly as a key
else
{
key = currentArg.Substring(keyStartIndex, separator - keyStartIndex);
}
value = currentArg.Substring(separator + 1);
}
// Override value when key is duplicated. So we always have the last argument win.
data[key] = value;
}
}
Data = data;
}
private Dictionary GetValidatedSwitchMappingsCopy(IDictionary switchMappings)
{
// The dictionary passed in might be constructed with a case-sensitive comparer
// However, the keys in configuration providers are all case-insensitive
// So we check whether the given switch mappings contain duplicated keys with case-insensitive comparer
var switchMappingsCopy = new Dictionary(StringComparer.OrdinalIgnoreCase);
foreach (var mapping in switchMappings)
{
// Only keys start with "--" or "-" are acceptable
if (!mapping.Key.StartsWith("-") && !mapping.Key.StartsWith("--"))
{
throw new ArgumentException(
Resources.FormatError_InvalidSwitchMapping(mapping.Key),
nameof(switchMappings));
}
if (switchMappingsCopy.ContainsKey(mapping.Key))
{
throw new ArgumentException(
Resources.FormatError_DuplicatedKeyInSwitchMappings(mapping.Key),
nameof(switchMappings));
}
switchMappingsCopy.Add(mapping.Key, mapping.Value);
}
return switchMappingsCopy;
}
}
}
================================================
FILE: src/Config.CommandLine/CommandLineConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
namespace Microsoft.Extensions.Configuration.CommandLine
{
///
/// Represents command line arguments as an .
///
public class CommandLineConfigurationSource : IConfigurationSource
{
///
/// Gets or sets the switch mappings.
///
public IDictionary SwitchMappings { get; set; }
///
/// Gets or sets the command line args.
///
public IEnumerable Args { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public IConfigurationProvider Build(IConfigurationBuilder builder)
{
return new CommandLineConfigurationProvider(Args, SwitchMappings);
}
}
}
================================================
FILE: src/Config.CommandLine/Config.CommandLine.csproj
================================================
Microsoft.Extensions.Configuration.CommandLine
Microsoft.Extensions.Configuration.CommandLine
Command line configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);commandline
================================================
FILE: src/Config.CommandLine/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.CommandLine.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.CommandLine/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.CommandLine
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.CommandLine.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// Keys in switch mappings are case-insensitive. A duplicated key '{0}' was found.
///
internal static string Error_DuplicatedKeyInSwitchMappings
{
get => GetString("Error_DuplicatedKeyInSwitchMappings");
}
///
/// Keys in switch mappings are case-insensitive. A duplicated key '{0}' was found.
///
internal static string FormatError_DuplicatedKeyInSwitchMappings(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_DuplicatedKeyInSwitchMappings"), p0);
///
/// The switch mappings contain an invalid switch '{0}'.
///
internal static string Error_InvalidSwitchMapping
{
get => GetString("Error_InvalidSwitchMapping");
}
///
/// The switch mappings contain an invalid switch '{0}'.
///
internal static string FormatError_InvalidSwitchMapping(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_InvalidSwitchMapping"), p0);
///
/// The short switch '{0}' is not defined in the switch mappings.
///
internal static string Error_ShortSwitchNotDefined
{
get => GetString("Error_ShortSwitchNotDefined");
}
///
/// The short switch '{0}' is not defined in the switch mappings.
///
internal static string FormatError_ShortSwitchNotDefined(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_ShortSwitchNotDefined"), p0);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.CommandLine/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Keys in switch mappings are case-insensitive. A duplicated key '{0}' was found.
The switch mappings contain an invalid switch '{0}'.
The short switch '{0}' is not defined in the switch mappings.
================================================
FILE: src/Config.CommandLine/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.CommandLine, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.CommandLineConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddCommandLine",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "args",
"Type": "System.String[]"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddCommandLine",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "args",
"Type": "System.String[]"
},
{
"Name": "switchMappings",
"Type": "System.Collections.Generic.IDictionary"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddCommandLine",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.CommandLine.CommandLineConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.ConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Args",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "args",
"Type": "System.Collections.Generic.IEnumerable"
},
{
"Name": "switchMappings",
"Type": "System.Collections.Generic.IDictionary",
"DefaultValue": "null"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.CommandLine.CommandLineConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
],
"Members": [
{
"Kind": "Method",
"Name": "get_SwitchMappings",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IDictionary",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_SwitchMappings",
"Parameters": [
{
"Name": "value",
"Type": "System.Collections.Generic.IDictionary"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Args",
"Parameters": [],
"ReturnType": "System.Collections.Generic.IEnumerable",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Args",
"Parameters": [
{
"Name": "value",
"Type": "System.Collections.Generic.IEnumerable"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.EnvironmentVariables/Config.EnvironmentVariables.csproj
================================================
Microsoft.Extensions.Configuration.EnvironmentVariables
Microsoft.Extensions.Configuration.EnvironmentVariables
Environment variables configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);envvar;environmentvariable
================================================
FILE: src/Config.EnvironmentVariables/EnvironmentVariablesConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
namespace Microsoft.Extensions.Configuration.EnvironmentVariables
{
///
/// An environment variable based .
///
public class EnvironmentVariablesConfigurationProvider : ConfigurationProvider
{
private const string MySqlServerPrefix = "MYSQLCONNSTR_";
private const string SqlAzureServerPrefix = "SQLAZURECONNSTR_";
private const string SqlServerPrefix = "SQLCONNSTR_";
private const string CustomPrefix = "CUSTOMCONNSTR_";
private const string ConnStrKeyFormat = "ConnectionStrings:{0}";
private const string ProviderKeyFormat = "ConnectionStrings:{0}_ProviderName";
private readonly string _prefix;
///
/// Initializes a new instance.
///
public EnvironmentVariablesConfigurationProvider() : this(string.Empty)
{ }
///
/// Initializes a new instance with the specified prefix.
///
/// A prefix used to filter the environment variables.
public EnvironmentVariablesConfigurationProvider(string prefix)
{
_prefix = prefix ?? string.Empty;
}
///
/// Loads the environment variables.
///
public override void Load()
{
Load(Environment.GetEnvironmentVariables());
}
internal void Load(IDictionary envVariables)
{
Data = new Dictionary(StringComparer.OrdinalIgnoreCase);
var filteredEnvVariables = envVariables
.Cast()
.SelectMany(AzureEnvToAppEnv)
.Where(entry => ((string)entry.Key).StartsWith(_prefix, StringComparison.OrdinalIgnoreCase));
foreach (var envVariable in filteredEnvVariables)
{
var key = ((string)envVariable.Key).Substring(_prefix.Length);
Data[key] = (string)envVariable.Value;
}
}
private static string NormalizeKey(string key)
{
return key.Replace("__", ConfigurationPath.KeyDelimiter);
}
private static IEnumerable AzureEnvToAppEnv(DictionaryEntry entry)
{
var key = (string)entry.Key;
var prefix = string.Empty;
var provider = string.Empty;
if (key.StartsWith(MySqlServerPrefix, StringComparison.OrdinalIgnoreCase))
{
prefix = MySqlServerPrefix;
provider = "MySql.Data.MySqlClient";
}
else if (key.StartsWith(SqlAzureServerPrefix, StringComparison.OrdinalIgnoreCase))
{
prefix = SqlAzureServerPrefix;
provider = "System.Data.SqlClient";
}
else if (key.StartsWith(SqlServerPrefix, StringComparison.OrdinalIgnoreCase))
{
prefix = SqlServerPrefix;
provider = "System.Data.SqlClient";
}
else if (key.StartsWith(CustomPrefix, StringComparison.OrdinalIgnoreCase))
{
prefix = CustomPrefix;
}
else
{
entry.Key = NormalizeKey(key);
yield return entry;
yield break;
}
// Return the key-value pair for connection string
yield return new DictionaryEntry(
string.Format(ConnStrKeyFormat, NormalizeKey(key.Substring(prefix.Length))),
entry.Value);
if (!string.IsNullOrEmpty(provider))
{
// Return the key-value pair for provider name
yield return new DictionaryEntry(
string.Format(ProviderKeyFormat, NormalizeKey(key.Substring(prefix.Length))),
provider);
}
}
}
}
================================================
FILE: src/Config.EnvironmentVariables/EnvironmentVariablesConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration.EnvironmentVariables
{
///
/// Represents environment variables as an .
///
public class EnvironmentVariablesConfigurationSource : IConfigurationSource
{
///
/// A prefix used to filter environment variables.
///
public string Prefix { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public IConfigurationProvider Build(IConfigurationBuilder builder)
{
return new EnvironmentVariablesConfigurationProvider(Prefix);
}
}
}
================================================
FILE: src/Config.EnvironmentVariables/EnvironmentVariablesExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.Extensions.Configuration.EnvironmentVariables;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for registering with .
///
public static class EnvironmentVariablesExtensions
{
///
/// Adds an that reads configuration values from environment variables.
///
/// The to add to.
/// The .
public static IConfigurationBuilder AddEnvironmentVariables(this IConfigurationBuilder configurationBuilder)
{
configurationBuilder.Add(new EnvironmentVariablesConfigurationSource());
return configurationBuilder;
}
///
/// Adds an that reads configuration values from environment variables
/// with a specified prefix.
///
/// The to add to.
/// The prefix that environment variable names must start with. The prefix will be removed from the environment variable names.
/// The .
public static IConfigurationBuilder AddEnvironmentVariables(
this IConfigurationBuilder configurationBuilder,
string prefix)
{
configurationBuilder.Add(new EnvironmentVariablesConfigurationSource { Prefix = prefix });
return configurationBuilder;
}
///
/// Adds an that reads configuration values from environment variables.
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddEnvironmentVariables(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.EnvironmentVariables/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.EnvironmentVariables.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.EnvironmentVariables/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.EnvironmentVariables, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.EnvironmentVariablesExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddEnvironmentVariables",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddEnvironmentVariables",
"Parameters": [
{
"Name": "configurationBuilder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "prefix",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddEnvironmentVariables",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.EnvironmentVariables.EnvironmentVariablesConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.ConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "prefix",
"Type": "System.String"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.EnvironmentVariables.EnvironmentVariablesConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
],
"Members": [
{
"Kind": "Method",
"Name": "get_Prefix",
"Parameters": [],
"ReturnType": "System.String",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Prefix",
"Parameters": [
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Sealed": true,
"Virtual": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.FileExtensions/Config.FileExtensions.csproj
================================================
Microsoft.Extensions.Configuration.FileExtensions
Microsoft.Extensions.Configuration.FileExtensions
Extension methods for configuring file-based configuration providers for Microsoft.Extensions.Configuration.
netstandard2.0
================================================
FILE: src/Config.FileExtensions/FileConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for .
///
public static class FileConfigurationExtensions
{
private static string FileProviderKey = "FileProvider";
private static string FileLoadExceptionHandlerKey = "FileLoadExceptionHandler";
///
/// Sets the default to be used for file-based providers.
///
/// The to add to.
/// The default file provider instance.
/// The .
public static IConfigurationBuilder SetFileProvider(this IConfigurationBuilder builder, IFileProvider fileProvider)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
builder.Properties[FileProviderKey] = fileProvider ?? throw new ArgumentNullException(nameof(fileProvider));
return builder;
}
///
/// Gets the default to be used for file-based providers.
///
/// The .
/// The .
public static IFileProvider GetFileProvider(this IConfigurationBuilder builder)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (builder.Properties.TryGetValue(FileProviderKey, out object provider))
{
return builder.Properties[FileProviderKey] as IFileProvider;
}
return new PhysicalFileProvider(AppContext.BaseDirectory ?? string.Empty);
}
///
/// Sets the FileProvider for file-based providers to a PhysicalFileProvider with the base path.
///
/// The to add to.
/// The absolute path of file-based providers.
/// The .
public static IConfigurationBuilder SetBasePath(this IConfigurationBuilder builder, string basePath)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (basePath == null)
{
throw new ArgumentNullException(nameof(basePath));
}
return builder.SetFileProvider(new PhysicalFileProvider(basePath));
}
///
/// Sets a default action to be invoked for file-based providers when an error occurs.
///
/// The to add to.
/// The Action to be invoked on a file load exception.
/// The .
public static IConfigurationBuilder SetFileLoadExceptionHandler(this IConfigurationBuilder builder, Action handler)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
builder.Properties[FileLoadExceptionHandlerKey] = handler;
return builder;
}
///
/// Gets the default to be used for file-based providers.
///
/// The .
/// The .
public static Action GetFileLoadExceptionHandler(this IConfigurationBuilder builder)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (builder.Properties.TryGetValue(FileLoadExceptionHandlerKey, out object handler))
{
return builder.Properties[FileLoadExceptionHandlerKey] as Action;
}
return null;
}
}
}
================================================
FILE: src/Config.FileExtensions/FileConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;
using System.Threading;
using Microsoft.Extensions.Primitives;
namespace Microsoft.Extensions.Configuration
{
///
/// Base class for file based .
///
public abstract class FileConfigurationProvider : ConfigurationProvider
{
///
/// Initializes a new instance with the specified source.
///
/// The source settings.
public FileConfigurationProvider(FileConfigurationSource source)
{
if (source == null)
{
throw new ArgumentNullException(nameof(source));
}
Source = source;
if (Source.ReloadOnChange && Source.FileProvider != null)
{
ChangeToken.OnChange(
() => Source.FileProvider.Watch(Source.Path),
() => {
Thread.Sleep(Source.ReloadDelay);
Load(reload: true);
});
}
}
///
/// The source settings for this provider.
///
public FileConfigurationSource Source { get; }
private void Load(bool reload)
{
var file = Source.FileProvider?.GetFileInfo(Source.Path);
if (file == null || !file.Exists)
{
if (Source.Optional || reload) // Always optional on reload
{
Data = new Dictionary(StringComparer.OrdinalIgnoreCase);
}
else
{
var error = new StringBuilder($"The configuration file '{Source.Path}' was not found and is not optional.");
if (!string.IsNullOrEmpty(file?.PhysicalPath))
{
error.Append($" The physical path is '{file.PhysicalPath}'.");
}
throw new FileNotFoundException(error.ToString());
}
}
else
{
// Always create new Data on reload to drop old keys
if (reload)
{
Data = new Dictionary(StringComparer.OrdinalIgnoreCase);
}
using (var stream = file.CreateReadStream())
{
try
{
Load(stream);
}
catch (Exception e)
{
bool ignoreException = false;
if (Source.OnLoadException != null)
{
var exceptionContext = new FileLoadExceptionContext
{
Provider = this,
Exception = e
};
Source.OnLoadException.Invoke(exceptionContext);
ignoreException = exceptionContext.Ignore;
}
if (!ignoreException)
{
throw e;
}
}
}
}
// REVIEW: Should we raise this in the base as well / instead?
OnReload();
}
///
/// Loads the contents of the file at .
///
/// If Optional is false on the source and a
/// file does not exist at specified Path.
public override void Load()
{
Load(reload: false);
}
///
/// Loads this provider's data from a stream.
///
/// The stream to read.
public abstract void Load(Stream stream);
}
}
================================================
FILE: src/Config.FileExtensions/FileConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Represents a base class for file based .
///
public abstract class FileConfigurationSource : IConfigurationSource
{
///
/// Used to access the contents of the file.
///
public IFileProvider FileProvider { get; set; }
///
/// The path to the file.
///
public string Path { get; set; }
///
/// Determines if loading the file is optional.
///
public bool Optional { get; set; }
///
/// Determines whether the source will be loaded if the underlying file changes.
///
public bool ReloadOnChange { get; set; }
///
/// Number of milliseconds that reload will wait before calling Load. This helps
/// avoid triggering reload before a file is completely written. Default is 250.
///
public int ReloadDelay { get; set; } = 250;
///
/// Will be called if an uncaught exception occurs in FileConfigurationProvider.Load.
///
public Action OnLoadException { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public abstract IConfigurationProvider Build(IConfigurationBuilder builder);
///
/// Called to use any default settings on the builder like the FileProvider or FileLoadExceptionHandler.
///
/// The .
public void EnsureDefaults(IConfigurationBuilder builder)
{
FileProvider = FileProvider ?? builder.GetFileProvider();
OnLoadException = OnLoadException ?? builder.GetFileLoadExceptionHandler();
}
///
/// If no file provider has been set, for absolute Path, this will creates a physical file provider
/// for the nearest existing directory.
///
public void ResolveFileProvider()
{
if (FileProvider == null &&
!string.IsNullOrEmpty(Path) &&
System.IO.Path.IsPathRooted(Path))
{
var directory = System.IO.Path.GetDirectoryName(Path);
var pathToFile = System.IO.Path.GetFileName(Path);
while (!string.IsNullOrEmpty(directory) && !Directory.Exists(directory))
{
pathToFile = System.IO.Path.Combine(System.IO.Path.GetFileName(directory), pathToFile);
directory = System.IO.Path.GetDirectoryName(directory);
}
if (Directory.Exists(directory))
{
FileProvider = new PhysicalFileProvider(directory);
Path = pathToFile;
}
}
}
}
}
================================================
FILE: src/Config.FileExtensions/FileLoadExceptionContext.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
namespace Microsoft.Extensions.Configuration
{
///
/// Contains information about a file load exception.
///
public class FileLoadExceptionContext
{
///
/// The that caused the exception.
///
public FileConfigurationProvider Provider { get; set; }
///
/// The exception that occured in Load.
///
public Exception Exception { get; set; }
///
/// If true, the exception will not be rethrown.
///
public bool Ignore { get; set; }
}
}
================================================
FILE: src/Config.FileExtensions/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.FileExtensions.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.FileExtensions/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.FileExtensions
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.FileExtensions.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// The expected physical path was '{0}'.
///
internal static string Error_ExpectedPhysicalPath
{
get => GetString("Error_ExpectedPhysicalPath");
}
///
/// The expected physical path was '{0}'.
///
internal static string FormatError_ExpectedPhysicalPath(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_ExpectedPhysicalPath"), p0);
///
/// The configuration file '{0}' was not found and is not optional.
///
internal static string Error_FileNotFound
{
get => GetString("Error_FileNotFound");
}
///
/// The configuration file '{0}' was not found and is not optional.
///
internal static string FormatError_FileNotFound(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_FileNotFound"), p0);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.FileExtensions/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
The expected physical path was '{0}'.
The configuration file '{0}' was not found and is not optional.
================================================
FILE: src/Config.FileExtensions/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.FileExtensions, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.FileConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "SetFileProvider",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "fileProvider",
"Type": "Microsoft.Extensions.FileProviders.IFileProvider"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetFileProvider",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.FileProviders.IFileProvider",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "SetBasePath",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "basePath",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "SetFileLoadExceptionHandler",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "handler",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "GetFileLoadExceptionHandler",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "System.Action",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.FileConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"BaseType": "Microsoft.Extensions.Configuration.ConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Source",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.FileConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "stream",
"Type": "System.IO.Stream"
}
],
"ReturnType": "System.Void",
"Virtual": true,
"Abstract": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.FileConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.FileConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"ImplementedInterfaces": [
"Microsoft.Extensions.Configuration.IConfigurationSource"
],
"Members": [
{
"Kind": "Method",
"Name": "get_FileProvider",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.FileProviders.IFileProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_FileProvider",
"Parameters": [
{
"Name": "value",
"Type": "Microsoft.Extensions.FileProviders.IFileProvider"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Path",
"Parameters": [],
"ReturnType": "System.String",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Path",
"Parameters": [
{
"Name": "value",
"Type": "System.String"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Optional",
"Parameters": [],
"ReturnType": "System.Boolean",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Optional",
"Parameters": [
{
"Name": "value",
"Type": "System.Boolean"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_ReloadOnChange",
"Parameters": [],
"ReturnType": "System.Boolean",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_ReloadOnChange",
"Parameters": [
{
"Name": "value",
"Type": "System.Boolean"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_ReloadDelay",
"Parameters": [],
"ReturnType": "System.Int32",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_ReloadDelay",
"Parameters": [
{
"Name": "value",
"Type": "System.Int32"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_OnLoadException",
"Parameters": [],
"ReturnType": "System.Action",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_OnLoadException",
"Parameters": [
{
"Name": "value",
"Type": "System.Action"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Virtual": true,
"Abstract": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "EnsureDefaults",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "ResolveFileProvider",
"Parameters": [],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Protected",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.FileLoadExceptionContext",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "get_Provider",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.FileConfigurationProvider",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Provider",
"Parameters": [
{
"Name": "value",
"Type": "Microsoft.Extensions.Configuration.FileConfigurationProvider"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Exception",
"Parameters": [],
"ReturnType": "System.Exception",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Exception",
"Parameters": [
{
"Name": "value",
"Type": "System.Exception"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "get_Ignore",
"Parameters": [],
"ReturnType": "System.Boolean",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "set_Ignore",
"Parameters": [
{
"Name": "value",
"Type": "System.Boolean"
}
],
"ReturnType": "System.Void",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.Ini/Config.Ini.csproj
================================================
Microsoft.Extensions.Configuration.Ini
Microsoft.Extensions.Configuration.Ini
INI configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);ini
================================================
FILE: src/Config.Ini/IniConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using Microsoft.Extensions.Configuration.Ini;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for adding .
///
public static class IniConfigurationExtensions
{
///
/// Adds the INI configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// The .
public static IConfigurationBuilder AddIniFile(this IConfigurationBuilder builder, string path)
{
return AddIniFile(builder, provider: null, path: path, optional: false, reloadOnChange: false);
}
///
/// Adds the INI configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// The .
public static IConfigurationBuilder AddIniFile(this IConfigurationBuilder builder, string path, bool optional)
{
return AddIniFile(builder, provider: null, path: path, optional: optional, reloadOnChange: false);
}
///
/// Adds the INI configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddIniFile(this IConfigurationBuilder builder, string path, bool optional, bool reloadOnChange)
{
return AddIniFile(builder, provider: null, path: path, optional: optional, reloadOnChange: reloadOnChange);
}
///
/// Adds a INI configuration source to .
///
/// The to add to.
/// The to use to access the file.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddIniFile(this IConfigurationBuilder builder, IFileProvider provider, string path, bool optional, bool reloadOnChange)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (string.IsNullOrEmpty(path))
{
throw new ArgumentException(Resources.Error_InvalidFilePath, nameof(path));
}
return builder.AddIniFile(s =>
{
s.FileProvider = provider;
s.Path = path;
s.Optional = optional;
s.ReloadOnChange = reloadOnChange;
s.ResolveFileProvider();
});
}
///
/// Adds a INI configuration source to .
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddIniFile(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.Ini/IniConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.IO;
namespace Microsoft.Extensions.Configuration.Ini
{
///
/// An INI file based .
/// Files are simple line structures (INI Files on Wikipedia )
///
///
/// [Section:Header]
/// key1=value1
/// key2 = " value2 "
/// ; comment
/// # comment
/// / comment
///
public class IniConfigurationProvider : FileConfigurationProvider
{
///
/// Initializes a new instance with the specified source.
///
/// The source settings.
public IniConfigurationProvider(IniConfigurationSource source) : base(source) { }
///
/// Loads the INI data from a stream.
///
/// The stream to read.
public override void Load(Stream stream)
{
var data = new Dictionary(StringComparer.OrdinalIgnoreCase);
using (var reader = new StreamReader(stream))
{
var sectionPrefix = string.Empty;
while (reader.Peek() != -1)
{
var rawLine = reader.ReadLine();
var line = rawLine.Trim();
// Ignore blank lines
if (string.IsNullOrWhiteSpace(line))
{
continue;
}
// Ignore comments
if (line[0] == ';' || line[0] == '#' || line[0] == '/')
{
continue;
}
// [Section:header]
if (line[0] == '[' && line[line.Length - 1] == ']')
{
// remove the brackets
sectionPrefix = line.Substring(1, line.Length - 2) + ConfigurationPath.KeyDelimiter;
continue;
}
// key = value OR "value"
int separator = line.IndexOf('=');
if (separator < 0)
{
throw new FormatException(Resources.FormatError_UnrecognizedLineFormat(rawLine));
}
string key = sectionPrefix + line.Substring(0, separator).Trim();
string value = line.Substring(separator + 1).Trim();
// Remove quotes
if (value.Length > 1 && value[0] == '"' && value[value.Length - 1] == '"')
{
value = value.Substring(1, value.Length - 2);
}
if (data.ContainsKey(key))
{
throw new FormatException(Resources.FormatError_KeyIsDuplicated(key));
}
data[key] = value;
}
}
Data = data;
}
}
}
================================================
FILE: src/Config.Ini/IniConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration.Ini
{
///
/// Represents an INI file as an .
/// Files are simple line structures (INI Files on Wikipedia )
///
///
/// [Section:Header]
/// key1=value1
/// key2 = " value2 "
/// ; comment
/// # comment
/// / comment
///
public class IniConfigurationSource : FileConfigurationSource
{
///
/// Builds the for this source.
///
/// The .
/// An
public override IConfigurationProvider Build(IConfigurationBuilder builder)
{
EnsureDefaults(builder);
return new IniConfigurationProvider(this);
}
}
}
================================================
FILE: src/Config.Ini/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.Ini.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.Ini/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.Ini
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.Ini.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// File path must be a non-empty string.
///
internal static string Error_InvalidFilePath
{
get => GetString("Error_InvalidFilePath");
}
///
/// File path must be a non-empty string.
///
internal static string FormatError_InvalidFilePath()
=> GetString("Error_InvalidFilePath");
///
/// A duplicate key '{0}' was found.
///
internal static string Error_KeyIsDuplicated
{
get => GetString("Error_KeyIsDuplicated");
}
///
/// A duplicate key '{0}' was found.
///
internal static string FormatError_KeyIsDuplicated(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_KeyIsDuplicated"), p0);
///
/// Unrecognized line format: '{0}'.
///
internal static string Error_UnrecognizedLineFormat
{
get => GetString("Error_UnrecognizedLineFormat");
}
///
/// Unrecognized line format: '{0}'.
///
internal static string FormatError_UnrecognizedLineFormat(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_UnrecognizedLineFormat"), p0);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.Ini/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
File path must be a non-empty string.
A duplicate key '{0}' was found.
Unrecognized line format: '{0}'.
================================================
FILE: src/Config.Ini/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.Ini, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.IniConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddIniFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddIniFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddIniFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddIniFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "provider",
"Type": "Microsoft.Extensions.FileProviders.IFileProvider"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddIniFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Ini.IniConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "stream",
"Type": "System.IO.Stream"
}
],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.Ini.IniConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Ini.IniConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationSource",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.Json/Config.Json.csproj
================================================
Microsoft.Extensions.Configuration.Json
Microsoft.Extensions.Configuration.Json
JSON configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);json
================================================
FILE: src/Config.Json/JsonConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using Microsoft.Extensions.Configuration.Json;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for adding .
///
public static class JsonConfigurationExtensions
{
///
/// Adds the JSON configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// The .
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path)
{
return AddJsonFile(builder, provider: null, path: path, optional: false, reloadOnChange: false);
}
///
/// Adds the JSON configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// The .
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path, bool optional)
{
return AddJsonFile(builder, provider: null, path: path, optional: optional, reloadOnChange: false);
}
///
/// Adds the JSON configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path, bool optional, bool reloadOnChange)
{
return AddJsonFile(builder, provider: null, path: path, optional: optional, reloadOnChange: reloadOnChange);
}
///
/// Adds a JSON configuration source to .
///
/// The to add to.
/// The to use to access the file.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, IFileProvider provider, string path, bool optional, bool reloadOnChange)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (string.IsNullOrEmpty(path))
{
throw new ArgumentException(Resources.Error_InvalidFilePath, nameof(path));
}
return builder.AddJsonFile(s =>
{
s.FileProvider = provider;
s.Path = path;
s.Optional = optional;
s.ReloadOnChange = reloadOnChange;
s.ResolveFileProvider();
});
}
///
/// Adds a JSON configuration source to .
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.Json/JsonConfigurationFileParser.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
using System.Linq;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
namespace Microsoft.Extensions.Configuration.Json
{
internal class JsonConfigurationFileParser
{
private JsonConfigurationFileParser() { }
private readonly IDictionary _data = new SortedDictionary(StringComparer.OrdinalIgnoreCase);
private readonly Stack _context = new Stack();
private string _currentPath;
private JsonTextReader _reader;
public static IDictionary Parse(Stream input)
=> new JsonConfigurationFileParser().ParseStream(input);
private IDictionary ParseStream(Stream input)
{
_data.Clear();
_reader = new JsonTextReader(new StreamReader(input));
_reader.DateParseHandling = DateParseHandling.None;
var jsonConfig = JObject.Load(_reader);
VisitJObject(jsonConfig);
return _data;
}
private void VisitJObject(JObject jObject)
{
foreach (var property in jObject.Properties())
{
EnterContext(property.Name);
VisitProperty(property);
ExitContext();
}
}
private void VisitProperty(JProperty property)
{
VisitToken(property.Value);
}
private void VisitToken(JToken token)
{
switch (token.Type)
{
case JTokenType.Object:
VisitJObject(token.Value());
break;
case JTokenType.Array:
VisitArray(token.Value());
break;
case JTokenType.Integer:
case JTokenType.Float:
case JTokenType.String:
case JTokenType.Boolean:
case JTokenType.Bytes:
case JTokenType.Raw:
case JTokenType.Null:
VisitPrimitive(token.Value());
break;
default:
throw new FormatException(Resources.FormatError_UnsupportedJSONToken(
_reader.TokenType,
_reader.Path,
_reader.LineNumber,
_reader.LinePosition));
}
}
private void VisitArray(JArray array)
{
for (int index = 0; index < array.Count; index++)
{
EnterContext(index.ToString());
VisitToken(array[index]);
ExitContext();
}
}
private void VisitPrimitive(JValue data)
{
var key = _currentPath;
if (_data.ContainsKey(key))
{
throw new FormatException(Resources.FormatError_KeyIsDuplicated(key));
}
_data[key] = data.ToString(CultureInfo.InvariantCulture);
}
private void EnterContext(string context)
{
_context.Push(context);
_currentPath = ConfigurationPath.Combine(_context.Reverse());
}
private void ExitContext()
{
_context.Pop();
_currentPath = ConfigurationPath.Combine(_context.Reverse());
}
}
}
================================================
FILE: src/Config.Json/JsonConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using Newtonsoft.Json;
namespace Microsoft.Extensions.Configuration.Json
{
///
/// A JSON file based .
///
public class JsonConfigurationProvider : FileConfigurationProvider
{
///
/// Initializes a new instance with the specified source.
///
/// The source settings.
public JsonConfigurationProvider(JsonConfigurationSource source) : base(source) { }
///
/// Loads the JSON data from a stream.
///
/// The stream to read.
public override void Load(Stream stream)
{
try
{
Data = JsonConfigurationFileParser.Parse(stream);
}
catch (JsonReaderException e)
{
string errorLine = string.Empty;
if (stream.CanSeek)
{
stream.Seek(0, SeekOrigin.Begin);
IEnumerable fileContent;
using (var streamReader = new StreamReader(stream))
{
fileContent = ReadLines(streamReader);
errorLine = RetrieveErrorContext(e, fileContent);
}
}
throw new FormatException(Resources.FormatError_JSONParseError(e.LineNumber, errorLine), e);
}
}
private static string RetrieveErrorContext(JsonReaderException e, IEnumerable fileContent)
{
string errorLine = null;
if (e.LineNumber >= 2)
{
var errorContext = fileContent.Skip(e.LineNumber - 2).Take(2).ToList();
// Handle situations when the line number reported is out of bounds
if (errorContext.Count() >= 2)
{
errorLine = errorContext[0].Trim() + Environment.NewLine + errorContext[1].Trim();
}
}
if (string.IsNullOrEmpty(errorLine))
{
var possibleLineContent = fileContent.Skip(e.LineNumber - 1).FirstOrDefault();
errorLine = possibleLineContent ?? string.Empty;
}
return errorLine;
}
private static IEnumerable ReadLines(StreamReader streamReader)
{
string line;
do
{
line = streamReader.ReadLine();
yield return line;
} while (line != null);
}
}
}
================================================
FILE: src/Config.Json/JsonConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
namespace Microsoft.Extensions.Configuration.Json
{
///
/// Represents a JSON file as an .
///
public class JsonConfigurationSource : FileConfigurationSource
{
///
/// Builds the for this source.
///
/// The .
/// A
public override IConfigurationProvider Build(IConfigurationBuilder builder)
{
EnsureDefaults(builder);
return new JsonConfigurationProvider(this);
}
}
}
================================================
FILE: src/Config.Json/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.Json.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.Json/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.Json
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.Json.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// File path must be a non-empty string.
///
internal static string Error_InvalidFilePath
{
get => GetString("Error_InvalidFilePath");
}
///
/// File path must be a non-empty string.
///
internal static string FormatError_InvalidFilePath()
=> GetString("Error_InvalidFilePath");
///
/// Could not parse the JSON file. Error on line number '{0}': '{1}'.
///
internal static string Error_JSONParseError
{
get => GetString("Error_JSONParseError");
}
///
/// Could not parse the JSON file. Error on line number '{0}': '{1}'.
///
internal static string FormatError_JSONParseError(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_JSONParseError"), p0, p1);
///
/// A duplicate key '{0}' was found.
///
internal static string Error_KeyIsDuplicated
{
get => GetString("Error_KeyIsDuplicated");
}
///
/// A duplicate key '{0}' was found.
///
internal static string FormatError_KeyIsDuplicated(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_KeyIsDuplicated"), p0);
///
/// Unsupported JSON token '{0}' was found. Path '{1}', line {2} position {3}.
///
internal static string Error_UnsupportedJSONToken
{
get => GetString("Error_UnsupportedJSONToken");
}
///
/// Unsupported JSON token '{0}' was found. Path '{1}', line {2} position {3}.
///
internal static string FormatError_UnsupportedJSONToken(object p0, object p1, object p2, object p3)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_UnsupportedJSONToken"), p0, p1, p2, p3);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.Json/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
File path must be a non-empty string.
Could not parse the JSON file. Error on line number '{0}': '{1}'.
A duplicate key '{0}' was found.
Unsupported JSON token '{0}' was found. Path '{1}', line {2} position {3}.
================================================
FILE: src/Config.Json/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.Json, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.JsonConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddJsonFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddJsonFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddJsonFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddJsonFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "provider",
"Type": "Microsoft.Extensions.FileProviders.IFileProvider"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddJsonFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Json.JsonConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "stream",
"Type": "System.IO.Stream"
}
],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.Json.JsonConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Json.JsonConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationSource",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.KeyPerFile/Config.KeyPerFile.csproj
================================================
Microsoft.Extensions.Configuration.KeyPerFile
Microsoft.Extensions.Configuration.KeyPerFile
Configuration provider that uses files in a directory for Microsoft.Extensions.Configuration.
netstandard2.0
false
================================================
FILE: src/Config.KeyPerFile/KeyPerFileConfigurationBuilderExtensions.cs
================================================
using System;
using System.IO;
using Microsoft.Extensions.Configuration.KeyPerFile;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for registering with .
///
public static class KeyPerFileConfigurationBuilderExtensions
{
///
/// Adds configuration using files from a directory. File names are used as the key,
/// file contents are used as the value.
///
/// The to add to.
/// The path to the directory.
/// Whether the directory is optional.
/// The .
public static IConfigurationBuilder AddKeyPerFile(this IConfigurationBuilder builder, string directoryPath, bool optional)
=> builder.AddKeyPerFile(source =>
{
// Only try to set the file provider if its not optional or the directory exists
if (!optional || Directory.Exists(directoryPath))
{
source.FileProvider = new PhysicalFileProvider(directoryPath);
}
source.Optional = optional;
});
///
/// Adds configuration using files from a directory. File names are used as the key,
/// file contents are used as the value.
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddKeyPerFile(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.KeyPerFile/KeyPerFileConfigurationProvider.cs
================================================
using System;
using System.Collections.Generic;
using System.IO;
namespace Microsoft.Extensions.Configuration.KeyPerFile
{
///
/// A that uses a directory's files as configuration key/values.
///
public class KeyPerFileConfigurationProvider : ConfigurationProvider
{
KeyPerFileConfigurationSource Source { get; set; }
///
/// Initializes a new instance.
///
/// The settings.
public KeyPerFileConfigurationProvider(KeyPerFileConfigurationSource source)
=> Source = source ?? throw new ArgumentNullException(nameof(source));
private static string NormalizeKey(string key)
=> key.Replace("__", ConfigurationPath.KeyDelimiter);
private static string TrimNewLine(string value)
=> value.EndsWith(Environment.NewLine)
? value.Substring(0, value.Length - Environment.NewLine.Length)
: value;
///
/// Loads the docker secrets.
///
public override void Load()
{
Data = new Dictionary(StringComparer.OrdinalIgnoreCase);
if (Source.FileProvider == null)
{
if (Source.Optional)
{
return;
}
else
{
throw new DirectoryNotFoundException("A non-null file provider for the directory is required when this source is not optional.");
}
}
var directory = Source.FileProvider.GetDirectoryContents("/");
if (!directory.Exists && !Source.Optional)
{
throw new DirectoryNotFoundException("The root directory for the FileProvider doesn't exist and is not optional.");
}
foreach (var file in directory)
{
if (file.IsDirectory)
{
continue;
}
using (var stream = file.CreateReadStream())
using (var streamReader = new StreamReader(stream))
{
if (Source.IgnoreCondition == null || !Source.IgnoreCondition(file.Name))
{
Data.Add(NormalizeKey(file.Name), TrimNewLine(streamReader.ReadToEnd()));
}
}
}
}
}
}
================================================
FILE: src/Config.KeyPerFile/KeyPerFileConfigurationSource.cs
================================================
using System;
using System.IO;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration.KeyPerFile
{
///
/// An used to configure .
///
public class KeyPerFileConfigurationSource : IConfigurationSource
{
///
/// Constructor;
///
public KeyPerFileConfigurationSource()
=> IgnoreCondition = s => IgnorePrefix != null && s.StartsWith(IgnorePrefix);
///
/// The FileProvider whos root "/" directory files will be used as configuration data.
///
public IFileProvider FileProvider { get; set; }
///
/// Files that start with this prefix will be excluded.
/// Defaults to "ignore.".
///
public string IgnorePrefix { get; set; } = "ignore.";
///
/// Used to determine if a file should be ignored using its name.
/// Defaults to using the IgnorePrefix.
///
public Func IgnoreCondition { get; set; }
///
/// If false, will throw if the directory doesn't exist.
///
public bool Optional { get; set; }
///
/// Builds the for this source.
///
/// The .
/// A
public IConfigurationProvider Build(IConfigurationBuilder builder)
=> new KeyPerFileConfigurationProvider(this);
}
}
================================================
FILE: src/Config.KeyPerFile/README.md
================================================
This is a configuration provider that uses a directory's files as data. A file's name is the key and the contents are the value.
================================================
FILE: src/Config.UserSecrets/Config.UserSecrets.csproj
================================================
Microsoft.Extensions.Configuration.UserSecrets
Microsoft.Extensions.Configuration.UserSecrets
Microsoft.Extensions.Configuration.UserSecrets
User secrets configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);secrets;usersecrets
================================================
FILE: src/Config.UserSecrets/PathHelper.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
namespace Microsoft.Extensions.Configuration.UserSecrets
{
///
/// Provides paths for user secrets configuration files.
///
public class PathHelper
{
internal const string SecretsFileName = "secrets.json";
///
///
/// Returns the path to the JSON file that stores user secrets.
///
///
/// This uses the current user profile to locate the secrets file on disk in a location outside of source control.
///
///
/// The user secret ID.
/// The full path to the secret file.
public static string GetSecretsPathFromSecretsId(string userSecretsId)
{
if (string.IsNullOrEmpty(userSecretsId))
{
throw new ArgumentException(Resources.Common_StringNullOrEmpty, nameof(userSecretsId));
}
var badCharIndex = userSecretsId.IndexOfAny(Path.GetInvalidFileNameChars());
if (badCharIndex != -1)
{
throw new InvalidOperationException(
string.Format(
Resources.Error_Invalid_Character_In_UserSecrets_Id,
userSecretsId[badCharIndex],
badCharIndex));
}
const string userSecretsFallbackDir = "DOTNET_USER_SECRETS_FALLBACK_DIR";
// For backwards compat, this checks env vars first before using Env.GetFolderPath
var root = Environment.GetEnvironmentVariable("APPDATA") // On Windows it goes to %APPDATA%\Microsoft\UserSecrets\
?? Environment.GetEnvironmentVariable("HOME") // On Mac/Linux it goes to ~/.microsoft/usersecrets/
?? Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)
?? Environment.GetFolderPath(Environment.SpecialFolder.UserProfile)
?? Environment.GetEnvironmentVariable(userSecretsFallbackDir); // this fallback is an escape hatch if everything else fails
if (string.IsNullOrEmpty(root))
{
throw new InvalidOperationException("Could not determine an appropriate location for storing user secrets. Set the " + userSecretsFallbackDir + " environment variable to a folder where user secrets should be stored.");
}
if (!string.IsNullOrEmpty(Environment.GetEnvironmentVariable("APPDATA")))
{
return Path.Combine(root, "Microsoft", "UserSecrets", userSecretsId, SecretsFileName);
}
else
{
return Path.Combine(root, ".microsoft", "usersecrets", userSecretsId, SecretsFileName);
}
}
}
}
================================================
FILE: src/Config.UserSecrets/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.UserSecrets.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.UserSecrets/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.UserSecrets
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.UserSecrets.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// Value cannot be null or an empty string.
///
internal static string Common_StringNullOrEmpty
{
get => GetString("Common_StringNullOrEmpty");
}
///
/// Value cannot be null or an empty string.
///
internal static string FormatCommon_StringNullOrEmpty()
=> GetString("Common_StringNullOrEmpty");
///
/// Invalid character '{0}' found in the user secrets ID at index '{1}'.
///
internal static string Error_Invalid_Character_In_UserSecrets_Id
{
get => GetString("Error_Invalid_Character_In_UserSecrets_Id");
}
///
/// Invalid character '{0}' found in the user secrets ID at index '{1}'.
///
internal static string FormatError_Invalid_Character_In_UserSecrets_Id(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_Invalid_Character_In_UserSecrets_Id"), p0, p1);
///
/// Could not find 'UserSecretsIdAttribute' on assembly '{0}'.
/// Check that the project for '{0}' has set the 'UserSecretsId' build property.
/// If the 'UserSecretsId' property is already set then add a reference to the Microsoft.Extensions.Configuration.UserSecrets package.
///
internal static string Error_Missing_UserSecretsIdAttribute
{
get => GetString("Error_Missing_UserSecretsIdAttribute");
}
///
/// Could not find 'UserSecretsIdAttribute' on assembly '{0}'.
/// Check that the project for '{0}' has set the 'UserSecretsId' build property.
/// If the 'UserSecretsId' property is already set then add a reference to the Microsoft.Extensions.Configuration.UserSecrets package.
///
internal static string FormatError_Missing_UserSecretsIdAttribute(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_Missing_UserSecretsIdAttribute"), p0);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.UserSecrets/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Value cannot be null or an empty string.
Invalid character '{0}' found in the user secrets ID at index '{1}'.
Could not find 'UserSecretsIdAttribute' on assembly '{0}'.
Check that the project for '{0}' has set the 'UserSecretsId' build property.
If the 'UserSecretsId' property is already set then add a reference to the Microsoft.Extensions.Configuration.UserSecrets package.
================================================
FILE: src/Config.UserSecrets/UserSecretsConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using System.Reflection;
using Microsoft.Extensions.Configuration.UserSecrets;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Configuration extensions for adding user secrets configuration source.
///
public static class UserSecretsConfigurationExtensions
{
///
///
/// Adds the user secrets configuration source. Searches the assembly that contains type
/// for an instance of , which specifies a user secrets ID.
///
///
/// A user secrets ID is unique value used to store and identify a collection of secret configuration values.
///
///
/// The configuration builder.
/// The type from the assembly to search for an instance of .
/// Thrown when the assembly containing does not have .
/// The configuration builder.
public static IConfigurationBuilder AddUserSecrets(this IConfigurationBuilder configuration)
where T : class
=> configuration.AddUserSecrets(optional: false);
///
///
/// Adds the user secrets configuration source. Searches the assembly that contains type
/// for an instance of , which specifies a user secrets ID.
///
///
/// A user secrets ID is unique value used to store and identify a collection of secret configuration values.
///
///
/// The configuration builder.
/// Whether loading secrets is optional. When false, this method may throw.
/// Thrown when is false and the assembly containing does not have a valid .
/// The type from the assembly to search for an instance of .
/// The configuration builder.
public static IConfigurationBuilder AddUserSecrets(this IConfigurationBuilder configuration, bool optional)
where T : class
=> configuration.AddUserSecrets(typeof(T).GetTypeInfo().Assembly, optional);
///
///
/// Adds the user secrets configuration source. This searches for an instance
/// of , which specifies a user secrets ID.
///
///
/// A user secrets ID is unique value used to store and identify a collection of secret configuration values.
///
///
/// The configuration builder.
/// The assembly with the .
/// Thrown when does not have a valid
/// The configuration builder.
public static IConfigurationBuilder AddUserSecrets(this IConfigurationBuilder configuration, Assembly assembly)
=> configuration.AddUserSecrets(assembly, optional: false);
///
///
/// Adds the user secrets configuration source. This searches for an instance
/// of , which specifies a user secrets ID.
///
///
/// A user secrets ID is unique value used to store and identify a collection of secret configuration values.
///
///
/// The configuration builder.
/// The assembly with the .
/// Whether loading secrets is optional. When false, this method may throw.
/// Thrown when is false and does not have a valid .
/// The configuration builder.
public static IConfigurationBuilder AddUserSecrets(this IConfigurationBuilder configuration, Assembly assembly, bool optional)
{
if (configuration == null)
{
throw new ArgumentNullException(nameof(configuration));
}
if (assembly == null)
{
throw new ArgumentNullException(nameof(assembly));
}
var attribute = assembly.GetCustomAttribute();
if (attribute != null)
{
return AddUserSecrets(configuration, attribute.UserSecretsId);
}
if (!optional)
{
throw new InvalidOperationException(Resources.FormatError_Missing_UserSecretsIdAttribute(assembly.GetName().Name));
}
return configuration;
}
///
///
/// Adds the user secrets configuration source with specified user secrets ID.
///
///
/// A user secrets ID is unique value used to store and identify a collection of secret configuration values.
///
///
/// The configuration builder.
/// The user secrets ID.
/// The configuration builder.
public static IConfigurationBuilder AddUserSecrets(this IConfigurationBuilder configuration, string userSecretsId)
{
if (configuration == null)
{
throw new ArgumentNullException(nameof(configuration));
}
if (userSecretsId == null)
{
throw new ArgumentNullException(nameof(userSecretsId));
}
return AddSecretsFile(configuration, PathHelper.GetSecretsPathFromSecretsId(userSecretsId));
}
private static IConfigurationBuilder AddSecretsFile(IConfigurationBuilder configuration, string secretPath)
{
var directoryPath = Path.GetDirectoryName(secretPath);
var fileProvider = Directory.Exists(directoryPath)
? new PhysicalFileProvider(directoryPath)
: null;
return configuration.AddJsonFile(fileProvider, PathHelper.SecretsFileName, optional: true, reloadOnChange: false);
}
}
}
================================================
FILE: src/Config.UserSecrets/UserSecretsIdAttribute.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
namespace Microsoft.Extensions.Configuration.UserSecrets
{
///
///
/// Represents the user secrets ID.
///
///
/// In most cases, this attribute is automatically generated during compilation by MSBuild targets
/// included in the UserSecrets NuGet package. These targets use the MSBuild property 'UserSecretsId'
/// to set the value for .
///
///
[AttributeUsage(AttributeTargets.Assembly, Inherited = false, AllowMultiple = false)]
public class UserSecretsIdAttribute : Attribute
{
///
/// Initializes an instance of .
///
/// The user secrets ID.
public UserSecretsIdAttribute(string userSecretId)
{
if (string.IsNullOrEmpty(userSecretId))
{
throw new ArgumentException(Resources.Common_StringNullOrEmpty, nameof(userSecretId));
}
UserSecretsId = userSecretId;
}
///
/// The user secrets ID.
///
public string UserSecretsId { get; }
}
}
================================================
FILE: src/Config.UserSecrets/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.UserSecrets, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.UserSecretsConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddUserSecrets",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"Class": true,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "AddUserSecrets",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "optional",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": [
{
"ParameterName": "T",
"ParameterPosition": 0,
"Class": true,
"BaseTypeOrInterfaces": []
}
]
},
{
"Kind": "Method",
"Name": "AddUserSecrets",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "assembly",
"Type": "System.Reflection.Assembly"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddUserSecrets",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "assembly",
"Type": "System.Reflection.Assembly"
},
{
"Name": "optional",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddUserSecrets",
"Parameters": [
{
"Name": "configuration",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "userSecretsId",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.UserSecrets.PathHelper",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "GetSecretsPathFromSecretsId",
"Parameters": [
{
"Name": "userSecretsId",
"Type": "System.String"
}
],
"ReturnType": "System.String",
"Static": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.UserSecrets.UserSecretsIdAttribute",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "System.Attribute",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "get_UserSecretsId",
"Parameters": [],
"ReturnType": "System.String",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "userSecretId",
"Type": "System.String"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Config.UserSecrets/build/netstandard2.0/Microsoft.Extensions.Configuration.UserSecrets.props
================================================
================================================
FILE: src/Config.UserSecrets/build/netstandard2.0/Microsoft.Extensions.Configuration.UserSecrets.targets
================================================
$(MSBuildAllProjects);$(MSBuildThisFileFullPath)
true
<_Parameter1>$(UserSecretsId.Trim())
================================================
FILE: src/Config.Xml/Config.Xml.csproj
================================================
Microsoft.Extensions.Configuration.Xml
Microsoft.Extensions.Configuration.Xml
XML configuration provider implementation for Microsoft.Extensions.Configuration.
netstandard2.0
$(PackageTags);xml
================================================
FILE: src/Config.Xml/Properties/AssemblyInfo.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Runtime.CompilerServices;
[assembly: InternalsVisibleTo("Microsoft.Extensions.Configuration.Xml.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")]
================================================
FILE: src/Config.Xml/Properties/Resources.Designer.cs
================================================
//
namespace Microsoft.Extensions.Configuration.Xml
{
using System.Globalization;
using System.Reflection;
using System.Resources;
internal static class Resources
{
private static readonly ResourceManager _resourceManager
= new ResourceManager("Microsoft.Extensions.Configuration.Xml.Resources", typeof(Resources).GetTypeInfo().Assembly);
///
/// File path must be a non-empty string.
///
internal static string Error_InvalidFilePath
{
get => GetString("Error_InvalidFilePath");
}
///
/// File path must be a non-empty string.
///
internal static string FormatError_InvalidFilePath()
=> GetString("Error_InvalidFilePath");
///
/// A duplicate key '{0}' was found.{1}
///
internal static string Error_KeyIsDuplicated
{
get => GetString("Error_KeyIsDuplicated");
}
///
/// A duplicate key '{0}' was found.{1}
///
internal static string FormatError_KeyIsDuplicated(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_KeyIsDuplicated"), p0, p1);
///
/// XML namespaces are not supported.{0}
///
internal static string Error_NamespaceIsNotSupported
{
get => GetString("Error_NamespaceIsNotSupported");
}
///
/// XML namespaces are not supported.{0}
///
internal static string FormatError_NamespaceIsNotSupported(object p0)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_NamespaceIsNotSupported"), p0);
///
/// Unsupported node type '{0}' was found.{1}
///
internal static string Error_UnsupportedNodeType
{
get => GetString("Error_UnsupportedNodeType");
}
///
/// Unsupported node type '{0}' was found.{1}
///
internal static string FormatError_UnsupportedNodeType(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Error_UnsupportedNodeType"), p0, p1);
///
/// Line {0}, position {1}.
///
internal static string Msg_LineInfo
{
get => GetString("Msg_LineInfo");
}
///
/// Line {0}, position {1}.
///
internal static string FormatMsg_LineInfo(object p0, object p1)
=> string.Format(CultureInfo.CurrentCulture, GetString("Msg_LineInfo"), p0, p1);
private static string GetString(string name, params string[] formatterNames)
{
var value = _resourceManager.GetString(name);
System.Diagnostics.Debug.Assert(value != null);
if (formatterNames != null)
{
for (var i = 0; i < formatterNames.Length; i++)
{
value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}");
}
}
return value;
}
}
}
================================================
FILE: src/Config.Xml/Resources.resx
================================================
text/microsoft-resx
2.0
System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
File path must be a non-empty string.
A duplicate key '{0}' was found.{1}
XML namespaces are not supported.{0}
Unsupported node type '{0}' was found.{1}
Line {0}, position {1}.
================================================
FILE: src/Config.Xml/XmlConfigurationExtensions.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using Microsoft.Extensions.Configuration.Xml;
using Microsoft.Extensions.FileProviders;
namespace Microsoft.Extensions.Configuration
{
///
/// Extension methods for adding .
///
public static class XmlConfigurationExtensions
{
///
/// Adds the XML configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// The .
public static IConfigurationBuilder AddXmlFile(this IConfigurationBuilder builder, string path)
{
return AddXmlFile(builder, provider: null, path: path, optional: false, reloadOnChange: false);
}
///
/// Adds the XML configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// The .
public static IConfigurationBuilder AddXmlFile(this IConfigurationBuilder builder, string path, bool optional)
{
return AddXmlFile(builder, provider: null, path: path, optional: optional, reloadOnChange: false);
}
///
/// Adds the XML configuration provider at to .
///
/// The to add to.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddXmlFile(this IConfigurationBuilder builder, string path, bool optional, bool reloadOnChange)
{
return AddXmlFile(builder, provider: null, path: path, optional: optional, reloadOnChange: reloadOnChange);
}
///
/// Adds a XML configuration source to .
///
/// The to add to.
/// The to use to access the file.
/// Path relative to the base path stored in
/// of .
/// Whether the file is optional.
/// Whether the configuration should be reloaded if the file changes.
/// The .
public static IConfigurationBuilder AddXmlFile(this IConfigurationBuilder builder, IFileProvider provider, string path, bool optional, bool reloadOnChange)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
if (string.IsNullOrEmpty(path))
{
throw new ArgumentException(Resources.Error_InvalidFilePath, nameof(path));
}
return builder.AddXmlFile(s =>
{
s.FileProvider = provider;
s.Path = path;
s.Optional = optional;
s.ReloadOnChange = reloadOnChange;
s.ResolveFileProvider();
});
}
///
/// Adds a XML configuration source to .
///
/// The to add to.
/// Configures the source.
/// The .
public static IConfigurationBuilder AddXmlFile(this IConfigurationBuilder builder, Action configureSource)
=> builder.Add(configureSource);
}
}
================================================
FILE: src/Config.Xml/XmlConfigurationProvider.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Xml;
namespace Microsoft.Extensions.Configuration.Xml
{
///
/// Represents an XML file as an .
///
public class XmlConfigurationProvider : FileConfigurationProvider
{
private const string NameAttributeKey = "Name";
///
/// Initializes a new instance with the specified source.
///
/// The source settings.
public XmlConfigurationProvider(XmlConfigurationSource source) : base(source) { }
internal XmlDocumentDecryptor Decryptor { get; set; } = XmlDocumentDecryptor.Instance;
///
/// Loads the XML data from a stream.
///
/// The stream to read.
public override void Load(Stream stream)
{
var data = new Dictionary(StringComparer.OrdinalIgnoreCase);
var readerSettings = new XmlReaderSettings()
{
CloseInput = false, // caller will close the stream
DtdProcessing = DtdProcessing.Prohibit,
IgnoreComments = true,
IgnoreWhitespace = true
};
using (var reader = Decryptor.CreateDecryptingXmlReader(stream, readerSettings))
{
var prefixStack = new Stack();
SkipUntilRootElement(reader);
// We process the root element individually since it doesn't contribute to prefix
ProcessAttributes(reader, prefixStack, data, AddNamePrefix);
ProcessAttributes(reader, prefixStack, data, AddAttributePair);
var preNodeType = reader.NodeType;
while (reader.Read())
{
switch (reader.NodeType)
{
case XmlNodeType.Element:
prefixStack.Push(reader.LocalName);
ProcessAttributes(reader, prefixStack, data, AddNamePrefix);
ProcessAttributes(reader, prefixStack, data, AddAttributePair);
// If current element is self-closing
if (reader.IsEmptyElement)
{
prefixStack.Pop();
}
break;
case XmlNodeType.EndElement:
if (prefixStack.Any())
{
// If this EndElement node comes right after an Element node,
// it means there is no text/CDATA node in current element
if (preNodeType == XmlNodeType.Element)
{
var key = ConfigurationPath.Combine(prefixStack.Reverse());
data[key] = string.Empty;
}
prefixStack.Pop();
}
break;
case XmlNodeType.CDATA:
case XmlNodeType.Text:
{
var key = ConfigurationPath.Combine(prefixStack.Reverse());
if (data.ContainsKey(key))
{
throw new FormatException(Resources.FormatError_KeyIsDuplicated(key,
GetLineInfo(reader)));
}
data[key] = reader.Value;
break;
}
case XmlNodeType.XmlDeclaration:
case XmlNodeType.ProcessingInstruction:
case XmlNodeType.Comment:
case XmlNodeType.Whitespace:
// Ignore certain types of nodes
break;
default:
throw new FormatException(Resources.FormatError_UnsupportedNodeType(reader.NodeType,
GetLineInfo(reader)));
}
preNodeType = reader.NodeType;
// If this element is a self-closing element,
// we pretend that we just processed an EndElement node
// because a self-closing element contains an end within itself
if (preNodeType == XmlNodeType.Element &&
reader.IsEmptyElement)
{
preNodeType = XmlNodeType.EndElement;
}
}
}
Data = data;
}
private void SkipUntilRootElement(XmlReader reader)
{
while (reader.Read())
{
if (reader.NodeType != XmlNodeType.XmlDeclaration &&
reader.NodeType != XmlNodeType.ProcessingInstruction)
{
break;
}
}
}
private static string GetLineInfo(XmlReader reader)
{
var lineInfo = reader as IXmlLineInfo;
return lineInfo == null ? string.Empty :
Resources.FormatMsg_LineInfo(lineInfo.LineNumber, lineInfo.LinePosition);
}
private void ProcessAttributes(XmlReader reader, Stack prefixStack, IDictionary data,
Action, IDictionary, XmlWriter> act, XmlWriter writer = null)
{
for (int i = 0; i < reader.AttributeCount; i++)
{
reader.MoveToAttribute(i);
// If there is a namespace attached to current attribute
if (!string.IsNullOrEmpty(reader.NamespaceURI))
{
throw new FormatException(Resources.FormatError_NamespaceIsNotSupported(GetLineInfo(reader)));
}
act(reader, prefixStack, data, writer);
}
// Go back to the element containing the attributes we just processed
reader.MoveToElement();
}
// The special attribute "Name" only contributes to prefix
// This method adds a prefix if current node in reader represents a "Name" attribute
private static void AddNamePrefix(XmlReader reader, Stack prefixStack,
IDictionary data, XmlWriter writer)
{
if (!string.Equals(reader.LocalName, NameAttributeKey, StringComparison.OrdinalIgnoreCase))
{
return;
}
// If current element is not root element
if (prefixStack.Any())
{
var lastPrefix = prefixStack.Pop();
prefixStack.Push(ConfigurationPath.Combine(lastPrefix, reader.Value));
}
else
{
prefixStack.Push(reader.Value);
}
}
// Common attributes contribute to key-value pairs
// This method adds a key-value pair if current node in reader represents a common attribute
private static void AddAttributePair(XmlReader reader, Stack prefixStack,
IDictionary data, XmlWriter writer)
{
prefixStack.Push(reader.LocalName);
var key = ConfigurationPath.Combine(prefixStack.Reverse());
if (data.ContainsKey(key))
{
throw new FormatException(Resources.FormatError_KeyIsDuplicated(key, GetLineInfo(reader)));
}
data[key] = reader.Value;
prefixStack.Pop();
}
}
}
================================================
FILE: src/Config.Xml/XmlConfigurationSource.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.Extensions.Configuration.Xml
{
///
/// An XML file based .
///
public class XmlConfigurationSource : FileConfigurationSource
{
///
/// Builds the for this source.
///
/// The .
/// A
public override IConfigurationProvider Build(IConfigurationBuilder builder)
{
EnsureDefaults(builder);
return new XmlConfigurationProvider(this);
}
}
}
================================================
FILE: src/Config.Xml/XmlDocumentDecryptor.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.IO;
using System.Security.Cryptography.Xml;
using System.Xml;
namespace Microsoft.Extensions.Configuration.Xml
{
///
/// Class responsible for encrypting and decrypting XML.
///
public class XmlDocumentDecryptor
{
///
/// Accesses the singleton decryptor instance.
///
public static readonly XmlDocumentDecryptor Instance = new XmlDocumentDecryptor();
private readonly Func _encryptedXmlFactory;
///
/// Initializes a XmlDocumentDecryptor.
///
// don't create an instance of this directly
protected XmlDocumentDecryptor()
: this(DefaultEncryptedXmlFactory)
{
}
// for testing only
internal XmlDocumentDecryptor(Func encryptedXmlFactory)
{
_encryptedXmlFactory = encryptedXmlFactory;
}
private static bool ContainsEncryptedData(XmlDocument document)
{
// EncryptedXml will simply decrypt the document in-place without telling
// us that it did so, so we need to perform a check to see if EncryptedXml
// will actually do anything. The below check for an encrypted data blob
// is the same one that EncryptedXml would have performed.
var namespaceManager = new XmlNamespaceManager(document.NameTable);
namespaceManager.AddNamespace("enc", "http://www.w3.org/2001/04/xmlenc#");
return (document.SelectSingleNode("//enc:EncryptedData", namespaceManager) != null);
}
///
/// Returns an XmlReader that decrypts data transparently.
///
public XmlReader CreateDecryptingXmlReader(Stream input, XmlReaderSettings settings)
{
// XML-based configurations aren't really all that big, so we can buffer
// the whole thing in memory while we determine decryption operations.
var memStream = new MemoryStream();
input.CopyTo(memStream);
memStream.Position = 0;
// First, consume the entire XmlReader as an XmlDocument.
var document = new XmlDocument();
using (var reader = XmlReader.Create(memStream, settings))
{
document.Load(reader);
}
memStream.Position = 0;
if (ContainsEncryptedData(document))
{
return DecryptDocumentAndCreateXmlReader(document);
}
else
{
// If no decryption would have taken place, return a new fresh reader
// based on the memory stream (which doesn't need to be disposed).
return XmlReader.Create(memStream, settings);
}
}
///
/// Creates a reader that can decrypt an encrypted XML document.
///
/// The document.
/// An XmlReader which can read the document.
protected virtual XmlReader DecryptDocumentAndCreateXmlReader(XmlDocument document)
{
// Perform the actual decryption step, updating the XmlDocument in-place.
var encryptedXml = _encryptedXmlFactory(document);
encryptedXml.DecryptDocument();
// Finally, return the new XmlReader from the updated XmlDocument.
// Error messages based on this XmlReader won't show line numbers,
// but that's fine since we transformed the document anyway.
return document.CreateNavigator().ReadSubtree();
}
private static EncryptedXml DefaultEncryptedXmlFactory(XmlDocument document)
=> new EncryptedXml(document);
}
}
================================================
FILE: src/Config.Xml/baseline.netcore.json
================================================
{
"AssemblyIdentity": "Microsoft.Extensions.Configuration.Xml, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60",
"Types": [
{
"Name": "Microsoft.Extensions.Configuration.XmlConfigurationExtensions",
"Visibility": "Public",
"Kind": "Class",
"Abstract": true,
"Static": true,
"Sealed": true,
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "AddXmlFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddXmlFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddXmlFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddXmlFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "provider",
"Type": "Microsoft.Extensions.FileProviders.IFileProvider"
},
{
"Name": "path",
"Type": "System.String"
},
{
"Name": "optional",
"Type": "System.Boolean"
},
{
"Name": "reloadOnChange",
"Type": "System.Boolean"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "AddXmlFile",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
},
{
"Name": "configureSource",
"Type": "System.Action"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationBuilder",
"Static": true,
"Extension": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Xml.XmlConfigurationProvider",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationProvider",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Load",
"Parameters": [
{
"Name": "stream",
"Type": "System.IO.Stream"
}
],
"ReturnType": "System.Void",
"Virtual": true,
"Override": true,
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [
{
"Name": "source",
"Type": "Microsoft.Extensions.Configuration.Xml.XmlConfigurationSource"
}
],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Xml.XmlConfigurationSource",
"Visibility": "Public",
"Kind": "Class",
"BaseType": "Microsoft.Extensions.Configuration.FileConfigurationSource",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "Build",
"Parameters": [
{
"Name": "builder",
"Type": "Microsoft.Extensions.Configuration.IConfigurationBuilder"
}
],
"ReturnType": "Microsoft.Extensions.Configuration.IConfigurationProvider",
"Virtual": true,
"Override": true,
"ImplementedInterface": "Microsoft.Extensions.Configuration.IConfigurationSource",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
},
{
"Name": "Microsoft.Extensions.Configuration.Xml.XmlDocumentDecryptor",
"Visibility": "Public",
"Kind": "Class",
"ImplementedInterfaces": [],
"Members": [
{
"Kind": "Method",
"Name": "CreateDecryptingXmlReader",
"Parameters": [
{
"Name": "input",
"Type": "System.IO.Stream"
},
{
"Name": "settings",
"Type": "System.Xml.XmlReaderSettings"
}
],
"ReturnType": "System.Xml.XmlReader",
"Visibility": "Public",
"GenericParameter": []
},
{
"Kind": "Method",
"Name": "DecryptDocumentAndCreateXmlReader",
"Parameters": [
{
"Name": "document",
"Type": "System.Xml.XmlDocument"
}
],
"ReturnType": "System.Xml.XmlReader",
"Virtual": true,
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Constructor",
"Name": ".ctor",
"Parameters": [],
"Visibility": "Protected",
"GenericParameter": []
},
{
"Kind": "Field",
"Name": "Instance",
"Parameters": [],
"ReturnType": "Microsoft.Extensions.Configuration.Xml.XmlDocumentDecryptor",
"Static": true,
"ReadOnly": true,
"Visibility": "Public",
"GenericParameter": []
}
],
"GenericParameters": []
}
]
}
================================================
FILE: src/Directory.Build.props
================================================
true
configuration
================================================
FILE: test/Config.AzureKeyVault.Test/AzureKeyVaultConfigurationTest.cs
================================================
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.Azure.KeyVault;
using Microsoft.Azure.KeyVault.Models;
using Microsoft.Extensions.Configuration.Test;
using Microsoft.Rest.Azure;
using Moq;
using Xunit;
namespace Microsoft.Extensions.Configuration.AzureKeyVault.Test
{
public class AzureKeyVaultConfigurationTest
{
private const string VaultUri = "https://vault";
[Fact]
public void LoadsAllSecretsFromVault()
{
var client = new Mock(MockBehavior.Strict);
var secret1Id = GetSecretId("Secret1");
var secret2Id = GetSecretId("Secret2");
client.Setup(c => c.GetSecretsAsync(VaultUri)).ReturnsAsync(new PageMock()
{
NextPageLink = "next",
Value = new[] { new SecretItem { Id = secret1Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretsNextAsync("next")).ReturnsAsync(new PageMock()
{
Value = new[] { new SecretItem { Id = secret2Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretAsync(secret1Id)).ReturnsAsync(new SecretBundle() { Value = "Value1", Id = secret1Id });
client.Setup(c => c.GetSecretAsync(secret2Id)).ReturnsAsync(new SecretBundle() { Value = "Value2", Id = secret2Id });
// Act
var provider = new AzureKeyVaultConfigurationProvider(client.Object, VaultUri, new DefaultKeyVaultSecretManager());
provider.Load();
// Assert
client.VerifyAll();
var childKeys = provider.GetChildKeys(Enumerable.Empty(), null).ToArray();
Assert.Equal(new[] { "Secret1", "Secret2" }, childKeys);
Assert.Equal("Value1", provider.Get("Secret1"));
Assert.Equal("Value2", provider.Get("Secret2"));
}
[Fact]
public void DoesNotLoadFilteredItems()
{
var client = new Mock(MockBehavior.Strict);
var secret1Id = GetSecretId("Secret1");
var secret2Id = GetSecretId("Secret2");
client.Setup(c => c.GetSecretsAsync(VaultUri)).ReturnsAsync(new PageMock()
{
Value = new[] { new SecretItem { Id = secret1Id, Attributes = new SecretAttributes { Enabled = true } }, new SecretItem { Id = secret2Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretAsync(secret1Id)).ReturnsAsync(new SecretBundle() { Value = "Value1", Id = secret1Id });
// Act
var provider = new AzureKeyVaultConfigurationProvider(client.Object, VaultUri, new EndsWithOneKeyVaultSecretManager());
provider.Load();
// Assert
client.VerifyAll();
var childKeys = provider.GetChildKeys(Enumerable.Empty(), null).ToArray();
Assert.Equal(new[] { "Secret1" }, childKeys);
Assert.Equal("Value1", provider.Get("Secret1"));
}
[Fact]
public void DoesNotLoadDisabledItems()
{
var client = new Mock(MockBehavior.Strict);
var secret1Id = GetSecretId("Secret1");
var secret2Id = GetSecretId("Secret2");
var secret3Id = GetSecretId("Secret3");
var secret4Id = GetSecretId("Secret4");
client.Setup(c => c.GetSecretsAsync(VaultUri)).ReturnsAsync(new PageMock()
{
NextPageLink = "next",
Value = new[] { new SecretItem { Id = secret1Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretsNextAsync("next")).ReturnsAsync(new PageMock()
{
Value = new[]
{
new SecretItem { Id = secret2Id, Attributes = new SecretAttributes { Enabled = false } },
new SecretItem { Id = secret3Id, Attributes = new SecretAttributes { Enabled = null } },
new SecretItem { Id = secret4Id, Attributes = null },
}
});
client.Setup(c => c.GetSecretAsync(secret1Id)).ReturnsAsync(new SecretBundle() { Value = "Value1", Id = secret1Id });
// Act
var provider = new AzureKeyVaultConfigurationProvider(client.Object, VaultUri, new DefaultKeyVaultSecretManager());
provider.Load();
// Assert
client.VerifyAll();
var childKeys = provider.GetChildKeys(Enumerable.Empty(), null).ToArray();
Assert.Equal(new[] { "Secret1" }, childKeys);
Assert.Equal("Value1", provider.Get("Secret1"));
Assert.Throws(() => provider.Get("Secret2"));
Assert.Throws(() => provider.Get("Secret3"));
Assert.Throws(() => provider.Get("Secret4"));
}
[Fact]
public void SupportsReload()
{
var client = new Mock(MockBehavior.Strict);
var secret1Id = GetSecretId("Secret1");
var value = "Value1";
client.Setup(c => c.GetSecretsAsync(VaultUri)).ReturnsAsync(new PageMock()
{
Value = new[] { new SecretItem { Id = secret1Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretAsync(secret1Id)).Returns((string id) => Task.FromResult(new SecretBundle() { Value = value, Id = id }));
// Act & Assert
var provider = new AzureKeyVaultConfigurationProvider(client.Object, VaultUri, new DefaultKeyVaultSecretManager());
provider.Load();
client.VerifyAll();
Assert.Equal("Value1", provider.Get("Secret1"));
value = "Value2";
provider.Load();
Assert.Equal("Value2", provider.Get("Secret1"));
}
[Fact]
public void ReplaceDoubleMinusInKeyName()
{
var client = new Mock(MockBehavior.Strict);
var secret1Id = GetSecretId("Section--Secret1");
client.Setup(c => c.GetSecretsAsync(VaultUri)).ReturnsAsync(new PageMock()
{
Value = new[] { new SecretItem { Id = secret1Id, Attributes = new SecretAttributes { Enabled = true } } }
});
client.Setup(c => c.GetSecretAsync(secret1Id)).ReturnsAsync(new SecretBundle() { Value = "Value1", Id = secret1Id });
// Act
var provider = new AzureKeyVaultConfigurationProvider(client.Object, VaultUri, new DefaultKeyVaultSecretManager());
provider.Load();
// Assert
client.VerifyAll();
Assert.Equal("Value1", provider.Get("Section:Secret1"));
}
[Fact]
public void ConstructorThrowsForNullManager()
{
Assert.Throws(() => new AzureKeyVaultConfigurationProvider(Mock.Of(), VaultUri, null));
}
private string GetSecretId(string name) => new SecretIdentifier(VaultUri, name).Identifier;
private class EndsWithOneKeyVaultSecretManager : DefaultKeyVaultSecretManager
{
public override bool Load(SecretItem secret)
{
return secret.Identifier.Name.EndsWith("1");
}
}
private class PageMock: IPage
{
public IEnumerable Value { get; set; }
public IEnumerator GetEnumerator()
{
return Value.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
public string NextPageLink { get; set; }
}
}
}
================================================
FILE: test/Config.AzureKeyVault.Test/Config.AzureKeyVault.Test.csproj
================================================
Microsoft.Extensions.Configuration.AzureKeyVault.Test
Microsoft.Extensions.Configuration.AzureKeyVault.Test
net461
================================================
FILE: test/Config.Binder.Test/Config.Binder.Test.csproj
================================================
Microsoft.Extensions.Configuration.Binder.Test
Microsoft.Extensions.Configuration.Binder.Test
netcoreapp2.2;net461
netcoreapp2.2
================================================
FILE: test/Config.Binder.Test/ConfigurationBinderTests.cs
================================================
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Reflection;
using Xunit;
namespace Microsoft.Extensions.Configuration.Binder.Test
{
public class ConfigurationBinderTests
{
public class ComplexOptions
{
public ComplexOptions()
{
Nested = new NestedOptions();
Virtual = "complex";
}
public NestedOptions Nested { get; set; }
public int Integer { get; set; }
public bool Boolean { get; set; }
public virtual string Virtual { get; set; }
public object Object { get; set; }
public string PrivateSetter { get; private set; }
public string ProtectedSetter { get; protected set; }
public string InternalSetter { get; internal set; }
public static string StaticProperty { get; set; }
private string PrivateProperty { get; set; }
internal string InternalProperty { get; set; }
protected string ProtectedProperty { get; set; }
protected string ProtectedPrivateSet { get; private set; }
private string PrivateReadOnly { get; }
internal string InternalReadOnly { get; }
protected string ProtectedReadOnly { get; }
public string ReadOnly
{
get { return null; }
}
}
public class NestedOptions
{
public int Integer { get; set; }
}
public class DerivedOptions : ComplexOptions
{
public override string Virtual
{
get
{
return base.Virtual;
}
set
{
base.Virtual = "Derived:" + value;
}
}
}
public class NullableOptions
{
public bool? MyNullableBool { get; set; }
public int? MyNullableInt { get; set; }
public DateTime? MyNullableDateTime { get; set; }
}
public class EnumOptions
{
public UriKind UriKind { get; set; }
}
public class GenericOptions
{
public T Value { get; set; }
}
public class ConfigurationInterfaceOptions
{
public IConfigurationSection Section { get; set; }
}
public class DerivedOptionsWithIConfigurationSection : DerivedOptions
{
public IConfigurationSection DerivedSection { get; set; }
}
[Fact]
public void CanBindIConfigurationSection()
{
var dic = new Dictionary
{
{"Section:Integer", "-2"},
{"Section:Boolean", "TRUe"},
{"Section:Nested:Integer", "11"},
{"Section:Virtual", "Sup"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = config.Get();
var childOptions = options.Section.Get();
Assert.True(childOptions.Boolean);
Assert.Equal(-2, childOptions.Integer);
Assert.Equal(11, childOptions.Nested.Integer);
Assert.Equal("Derived:Sup", childOptions.Virtual);
Assert.Equal("Section", options.Section.Key);
Assert.Equal("Section", options.Section.Path);
Assert.Null(options.Section.Value);
}
[Fact]
public void CanBindWithKeyOverload()
{
var dic = new Dictionary
{
{"Section:Integer", "-2"},
{"Section:Boolean", "TRUe"},
{"Section:Nested:Integer", "11"},
{"Section:Virtual", "Sup"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = new DerivedOptions();
config.Bind("Section", options);
Assert.True(options.Boolean);
Assert.Equal(-2, options.Integer);
Assert.Equal(11, options.Nested.Integer);
Assert.Equal("Derived:Sup", options.Virtual);
}
[Fact]
public void CanBindIConfigurationSectionWithDerivedOptionsSection()
{
var dic = new Dictionary
{
{"Section:Integer", "-2"},
{"Section:Boolean", "TRUe"},
{"Section:Nested:Integer", "11"},
{"Section:Virtual", "Sup"},
{"Section:DerivedSection:Nested:Integer", "11"},
{"Section:DerivedSection:Virtual", "Sup"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = config.Get();
var childOptions = options.Section.Get();
var childDerivedOptions = childOptions.DerivedSection.Get();
Assert.True(childOptions.Boolean);
Assert.Equal(-2, childOptions.Integer);
Assert.Equal(11, childOptions.Nested.Integer);
Assert.Equal("Derived:Sup", childOptions.Virtual);
Assert.Equal(11, childDerivedOptions.Nested.Integer);
Assert.Equal("Derived:Sup", childDerivedOptions.Virtual);
Assert.Equal("Section", options.Section.Key);
Assert.Equal("Section", options.Section.Path);
Assert.Equal("DerivedSection", childOptions.DerivedSection.Key);
Assert.Equal("Section:DerivedSection", childOptions.DerivedSection.Path);
Assert.Null(options.Section.Value);
}
[Fact]
public void EmptyStringIsNullable()
{
var dic = new Dictionary
{
{"empty", ""},
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
Assert.Null(config.GetValue("empty"));
Assert.Null(config.GetValue("empty"));
}
[Fact]
public void GetScalarNullable()
{
var dic = new Dictionary
{
{"Integer", "-2"},
{"Boolean", "TRUe"},
{"Nested:Integer", "11"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
Assert.True(config.GetValue("Boolean"));
Assert.Equal(-2, config.GetValue("Integer"));
Assert.Equal(11, config.GetValue("Nested:Integer"));
}
[Fact]
public void CanBindToObjectProperty()
{
var dic = new Dictionary
{
{"Object", "whatever" }
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = new ComplexOptions();
config.Bind(options);
Assert.Equal("whatever", options.Object);
}
[Fact]
public void GetNullValue()
{
var dic = new Dictionary
{
{"Integer", null},
{"Boolean", null},
{"Nested:Integer", null},
{"Object", null }
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
Assert.False(config.GetValue("Boolean"));
Assert.Equal(0, config.GetValue("Integer"));
Assert.Equal(0, config.GetValue("Nested:Integer"));
Assert.Null(config.GetValue("Object"));
Assert.False(config.GetSection("Boolean").Get());
Assert.Equal(0, config.GetSection("Integer").Get());
Assert.Equal(0, config.GetSection("Nested:Integer").Get());
Assert.Null(config.GetSection("Object").Get());
}
[Fact]
public void GetDefaultsWhenDataDoesNotExist()
{
var dic = new Dictionary
{
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
Assert.False(config.GetValue("Boolean"));
Assert.Equal(0, config.GetValue("Integer"));
Assert.Equal(0, config.GetValue("Nested:Integer"));
Assert.Null(config.GetValue("Object"));
Assert.True(config.GetValue("Boolean", true));
Assert.Equal(3, config.GetValue("Integer", 3));
Assert.Equal(1, config.GetValue("Nested:Integer", 1));
var foo = new ComplexOptions();
Assert.Same(config.GetValue("Object", foo), foo);
}
[Fact]
public void GetUri()
{
var dic = new Dictionary
{
{"AnUri", "http://www.bing.com"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var uri = config.GetValue("AnUri");
Assert.Equal("http://www.bing.com", uri.OriginalString);
}
[Theory]
[InlineData("2147483647", typeof(int))]
[InlineData("4294967295", typeof(uint))]
[InlineData("32767", typeof(short))]
[InlineData("65535", typeof(ushort))]
[InlineData("-9223372036854775808", typeof(long))]
[InlineData("18446744073709551615", typeof(ulong))]
[InlineData("trUE", typeof(bool))]
[InlineData("255", typeof(byte))]
[InlineData("127", typeof(sbyte))]
[InlineData("\uffff", typeof(char))]
[InlineData("79228162514264337593543950335", typeof(decimal))]
[InlineData("1.79769e+308", typeof(double))]
[InlineData("3.40282347E+38", typeof(float))]
[InlineData("2015-12-24T07:34:42-5:00", typeof(DateTime))]
[InlineData("12/24/2015 13:44:55 +4", typeof(DateTimeOffset))]
[InlineData("99.22:22:22.1234567", typeof(TimeSpan))]
[InlineData("http://www.bing.com", typeof(Uri))]
// enum test
[InlineData("Constructor", typeof(AttributeTargets))]
[InlineData("CA761232-ED42-11CE-BACD-00AA0057B223", typeof(Guid))]
public void CanReadAllSupportedTypes(string value, Type type)
{
// arrange
var dic = new Dictionary
{
{"Value", value}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var optionsType = typeof(GenericOptions<>).MakeGenericType(type);
var options = Activator.CreateInstance(optionsType);
var expectedValue = TypeDescriptor.GetConverter(type).ConvertFromInvariantString(value);
// act
config.Bind(options);
var optionsValue = options.GetType().GetProperty("Value").GetValue(options);
var getValueValue = config.GetValue(type, "Value");
var getValue = config.GetSection("Value").Get(type);
// assert
Assert.Equal(expectedValue, optionsValue);
Assert.Equal(expectedValue, getValue);
Assert.Equal(expectedValue, getValueValue);
}
[Theory]
[InlineData(typeof(int))]
[InlineData(typeof(uint))]
[InlineData(typeof(short))]
[InlineData(typeof(ushort))]
[InlineData(typeof(long))]
[InlineData(typeof(ulong))]
[InlineData(typeof(bool))]
[InlineData(typeof(byte))]
[InlineData(typeof(sbyte))]
[InlineData(typeof(char))]
[InlineData(typeof(decimal))]
[InlineData(typeof(double))]
[InlineData(typeof(float))]
[InlineData(typeof(DateTime))]
[InlineData(typeof(DateTimeOffset))]
[InlineData(typeof(TimeSpan))]
[InlineData(typeof(AttributeTargets))]
[InlineData(typeof(Guid))]
public void ConsistentExceptionOnFailedBinding(Type type)
{
// arrange
const string IncorrectValue = "Invalid data";
var dic = new Dictionary
{
{"Value", IncorrectValue}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var optionsType = typeof(GenericOptions<>).MakeGenericType(type);
var options = Activator.CreateInstance(optionsType);
// act
var exception = Assert.Throws(
() => config.Bind(options));
var getValueException = Assert.Throws(
() => config.GetValue(type, "Value"));
var getException = Assert.Throws(
() => config.GetSection("Value").Get(type));
// assert
Assert.NotNull(exception.InnerException);
Assert.NotNull(getException.InnerException);
Assert.Equal(
Resources.FormatError_FailedBinding(IncorrectValue, type),
exception.Message);
Assert.Equal(
Resources.FormatError_FailedBinding(IncorrectValue, type),
getException.Message);
Assert.Equal(
Resources.FormatError_FailedBinding(IncorrectValue, type),
getValueException.Message);
}
[Fact]
public void BinderIgnoresIndexerProperties()
{
var configurationBuilder = new ConfigurationBuilder();
var config = configurationBuilder.Build();
config.Bind(new List());
}
[Fact]
public void BindCanReadComplexProperties()
{
var dic = new Dictionary
{
{"Integer", "-2"},
{"Boolean", "TRUe"},
{"Nested:Integer", "11"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var instance = new ComplexOptions();
config.Bind(instance);
Assert.True(instance.Boolean);
Assert.Equal(-2, instance.Integer);
Assert.Equal(11, instance.Nested.Integer);
}
[Fact]
public void GetCanReadComplexProperties()
{
var dic = new Dictionary
{
{"Integer", "-2"},
{"Boolean", "TRUe"},
{"Nested:Integer", "11"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = new ComplexOptions();
config.Bind(options);
Assert.True(options.Boolean);
Assert.Equal(-2, options.Integer);
Assert.Equal(11, options.Nested.Integer);
}
[Fact]
public void BindCanReadInheritedProperties()
{
var dic = new Dictionary
{
{"Integer", "-2"},
{"Boolean", "TRUe"},
{"Nested:Integer", "11"},
{"Virtual", "Sup"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var instance = new DerivedOptions();
config.Bind(instance);
Assert.True(instance.Boolean);
Assert.Equal(-2, instance.Integer);
Assert.Equal(11, instance.Nested.Integer);
Assert.Equal("Derived:Sup", instance.Virtual);
}
[Fact]
public void GetCanReadInheritedProperties()
{
var dic = new Dictionary
{
{"Integer", "-2"},
{"Boolean", "TRUe"},
{"Nested:Integer", "11"},
{"Virtual", "Sup"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = new DerivedOptions();
config.Bind(options);
Assert.True(options.Boolean);
Assert.Equal(-2, options.Integer);
Assert.Equal(11, options.Nested.Integer);
Assert.Equal("Derived:Sup", options.Virtual);
}
[Fact]
public void GetCanReadStaticProperty()
{
var dic = new Dictionary
{
{"StaticProperty", "stuff"},
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = new ComplexOptions();
config.Bind(options);
Assert.Equal("stuff", ComplexOptions.StaticProperty);
}
[Fact]
public void BindCanReadStaticProperty()
{
var dic = new Dictionary
{
{"StaticProperty", "other stuff"},
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var instance = new ComplexOptions();
config.Bind(instance);
Assert.Equal("other stuff", ComplexOptions.StaticProperty);
}
[Fact]
public void CanGetComplexOptionsWhichHasAlsoHasValue()
{
var dic = new Dictionary
{
{"obj", "whut" },
{"obj:Integer", "-2"},
{"obj:Boolean", "TRUe"},
{"obj:Nested:Integer", "11"}
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = config.GetSection("obj").Get();
Assert.NotNull(options);
Assert.True(options.Boolean);
Assert.Equal(-2, options.Integer);
Assert.Equal(11, options.Nested.Integer);
}
[Theory]
[InlineData("ReadOnly")]
[InlineData("PrivateSetter")]
[InlineData("ProtectedSetter")]
[InlineData("InternalSetter")]
[InlineData("InternalProperty")]
[InlineData("PrivateProperty")]
[InlineData("ProtectedProperty")]
[InlineData("ProtectedPrivateSet")]
public void GetIgnoresTests(string property)
{
var dic = new Dictionary
{
{property, "stuff"},
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = config.Get();
Assert.Null(options.GetType().GetTypeInfo().GetDeclaredProperty(property).GetValue(options));
}
[Theory]
[InlineData("PrivateSetter")]
[InlineData("ProtectedSetter")]
[InlineData("InternalSetter")]
[InlineData("InternalProperty")]
[InlineData("PrivateProperty")]
[InlineData("ProtectedProperty")]
[InlineData("ProtectedPrivateSet")]
public void GetCanSetNonPublicWhenSet(string property)
{
var dic = new Dictionary
{
{property, "stuff"},
};
var configurationBuilder = new ConfigurationBuilder();
configurationBuilder.AddInMemoryCollection(dic);
var config = configurationBuilder.Build();
var options = config.Get