Nota
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare ad accedere o modificare le directory.
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare a modificare le directory.
Di Stephen Molloy e Rick Anderson
I generatori di configurazioni forniscono un meccanismo moderno e agile per ASP.NET app per ottenere valori di configurazione da origini esterne.
Generatori di configurazioni:
- Sono disponibili in .NET Framework 4.7.1 e versioni successive.
- Fornire un meccanismo flessibile per la lettura dei valori di configurazione.
- Soddisfare alcune delle esigenze di base delle app durante lo spostamento in un contenitore e in un ambiente incentrato sul cloud.
- Può essere usato per migliorare la protezione dei dati di configurazione mediante il disegno da origini precedentemente non disponibili (ad esempio, Azure Key Vault e variabili di ambiente) nel sistema di configurazione .NET.
Generatori di configurazioni chiave/valore
Uno scenario comune che può essere gestito dai generatori di configurazione consiste nel fornire un meccanismo di sostituzione chiave/valore di base per le sezioni di configurazione che seguono un modello chiave/valore. Il concetto di .NET Framework di ConfigurationBuilders non è limitato a sezioni o modelli di configurazione specifici. Tuttavia, molti dei generatori di configurazione in Microsoft.Configuration.ConfigurationBuilders (github, NuGet) funzionano all'interno del modello chiave/valore.
Impostazioni dei generatori di configurazioni chiave/valore
Le impostazioni seguenti si applicano a tutti i generatori di configurazioni chiave/valore in Microsoft.Configuration.ConfigurationBuilders.
Modalità
I generatori di configurazione usano un'origine esterna di informazioni chiave/valore per popolare gli elementi chiave/valore selezionati del sistema di configurazione. In particolare, le sezioni <appSettings/> e <connectionStrings/> ricevono un trattamento speciale dai generatori di configurazione. I costruttori funzionano in tre modalità:
Strict- Modalità predefinita. In questa modalità, il generatore di configurazione opera solo su sezioni di configurazione note incentrate su chiave/valore.Strictmodalità enumera ogni chiave nella sezione. Se viene trovata una chiave corrispondente nell'origine esterna:- I generatori di configurazione sostituiscono il valore nella sezione di configurazione risultante con il valore dell'origine esterna.
Greedy- Questa modalità è strettamente correlata allaStrictmodalità. Anziché essere limitati alle chiavi già presenti nella configurazione originale:- I generatori di configurazione aggiungono tutte le coppie chiave/valore dall'origine esterna alla sezione di configurazione risultante.
Expand- Opera sul codice XML non elaborato prima di essere analizzato in un oggetto sezione di configurazione. Può essere considerato come un'espansione di token in una stringa. Qualsiasi parte della stringa XML non elaborata che corrisponde al modello${token}è un candidato per l'espansione del token. Se nell'origine esterna non viene trovato alcun valore corrispondente, il token non viene modificato. I costruttori in questa modalità non sono limitati alle sezioni<appSettings/>e<connectionStrings/>.
Il markup seguente da web.config abilita il EnvironmentConfigBuilder in modalità Strict:
<configuration>
<configSections>
<section name="configBuilders"
type="System.Configuration.ConfigurationBuildersSection,
System.Configuration, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b03f5f7f11d50a3a"
restartOnExternalChanges="false" requirePermission="false" />
</configSections>
<configBuilders>
<builders>
<add name="MyEnvironment"
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment,
Version=1.0.0.0, Culture=neutral" />
</builders>
</configBuilders>
<appSettings configBuilders="MyEnvironment">
<add key="ServiceID" value="ServiceID value from web.config" />
<add key="ServiceKey" value="ServiceKey value from web.config" />
</appSettings>
<connectionStrings configBuilders="MyEnvironment">
<add name="default" connectionString="Data Source=web.config/mydb.db" />
</connectionStrings>
Il codice seguente legge <appSettings/> e <connectionStrings/> illustrato nel file web.config precedente:
using System;
using System.Configuration;
using System.Web.UI;
namespace MyConfigBuilders
{
public partial class About : Page
{
public string ServiceID { get; set; }
public string ServiceKey { get; set; }
public string ConString { get; set; }
protected void Page_Load(object sender, EventArgs e)
{
ServiceID = ConfigurationManager.AppSettings["ServiceID"];
ServiceKey = ConfigurationManager.AppSettings["ServiceKey"];
ConString = ConfigurationManager.ConnectionStrings["default"]
?.ConnectionString;
}
}
}
Il codice precedente imposta i valori della proprietà su:
- I valori nel file web.config se le chiavi non sono impostate nelle variabili di ambiente.
- Valori della variabile di ambiente, se impostata.
Ad esempio, ServiceID conterrà:
- "Valore ServiceID da web.config", se la variabile di ambiente
ServiceIDnon è impostata. - Valore della
ServiceIDvariabile di ambiente, se impostato.
L'immagine seguente mostra le <appSettings/> chiavi/valori del file web.config precedente impostato nell'editor dell'ambiente:
Nota: potrebbe essere necessario uscire e riavviare Visual Studio per visualizzare le modifiche nelle variabili di ambiente.
Gestione dei prefissi
I prefissi chiave possono semplificare l'impostazione delle chiavi perché:
- La configurazione di .NET Framework è complessa e annidata.
- Le fonti chiave/valore esterne sono generalmente di base e semplici per natura. Ad esempio, le variabili di ambiente non sono annidate.
Usare uno degli approcci seguenti per inserire sia <appSettings/> che <connectionStrings/> nella configurazione tramite variabili di ambiente.
- Con la modalità
EnvironmentConfigBuilderpredefinitaStricte i nomi di chiave appropriati nel file di configurazione. Il codice e il markup precedenti accettano questo approccio. Con questo approccio non è possibile avere chiavi con lo stesso nome sia in<appSettings/>che in<connectionStrings/>. - Usare due
EnvironmentConfigBuilderin modalitàGreedycon prefissi distinti estripPrefix. Con questo approccio, l'app può leggere<appSettings/>e<connectionStrings/>senza dover aggiornare il file di configurazione. Nella sezione successiva, stripPrefix, viene illustrato come eseguire questa operazione. - Usare due
EnvironmentConfigBuilderin modalitàGreedycon prefissi distinti. Con questo approccio non è possibile avere nomi di chiave duplicati perché i nomi delle chiavi devono essere diversi per prefisso. Ad esempio:
<configuration>
<configSections>
<section name="configBuilders"
type="System.Configuration.ConfigurationBuildersSection,
System.Configuration, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b03f5f7f11d50a3a"
restartOnExternalChanges="false" requirePermission="false" />
</configSections>
<configBuilders>
<builders>
<add name="AS_Environment" mode="Greedy" prefix="AppSetting_"
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment" />
<add name="CS_Environment" mode="Greedy" prefix="ConnStr_"
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment" />
</builders>
</configBuilders>
<appSettings configBuilders="AS_Environment">
<add key="AppSetting_ServiceID" value="ServiceID value from web.config" />
<add key="AppSetting_default" value="AppSetting_default value from web.config" />
</appSettings>
<connectionStrings configBuilders="CS_Environment">
<add name="ConnStr_default" connectionString="Data Source=web.config/mydb.db" />
</connectionStrings>
Con il markup precedente, è possibile usare la stessa sorgente chiave/valore piatta per popolare la configurazione di due sezioni diverse.
L'immagine seguente mostra le chiavi/valori <appSettings/> e <connectionStrings/> del file web.config precedente impostato nell'editor dell'ambiente:
Il codice seguente legge le chiavi/valori <appSettings/> e <connectionStrings/> contenuti nel file web.config precedente.
public partial class Contact : Page
{
public string ServiceID { get; set; }
public string AppSetting_default { get; set; }
public string ConString { get; set; }
protected void Page_Load(object sender, EventArgs e)
{
ServiceID = ConfigurationManager.AppSettings["AppSetting_ServiceID"];
AppSetting_default = ConfigurationManager.AppSettings["AppSetting_default"];
ConString = ConfigurationManager.ConnectionStrings["ConnStr_default"]
?.ConnectionString;
}
}
Il codice precedente imposta i valori della proprietà su:
- I valori nel file web.config se le chiavi non sono impostate nelle variabili di ambiente.
- Valori della variabile di ambiente, se impostata.
Ad esempio, usando il file web.config precedente, le chiavi/valori nell'immagine dell'editor dell'ambiente precedente e il codice precedente, vengono impostati i valori seguenti:
| Chiave | valore |
|---|---|
| AppSetting_ServiceID | AppSetting_ServiceID dalle variabili d'ambiente |
| AppSetting_default | AppSetting_default valore da env |
| ConnStr_default | ConnStr_default valore da environment |
stripPrefix
stripPrefix: valore booleano, il valore predefinito è false.
Il markup XML precedente separa le impostazioni dell'app dalle stringa di connessione, ma richiede che tutte le chiavi nel file web.config usino il prefisso specificato. Ad esempio, il prefisso AppSetting deve essere aggiunto alla ServiceID chiave ("AppSetting_ServiceID"). Con stripPrefix, il prefisso non viene usato nel file web.config . Il prefisso è obbligatorio nell'origine del generatore di configurazione, ad esempio nell'ambiente. La maggior parte degli sviluppatori userà stripPrefix.
Le applicazioni in genere rimuovono il prefisso. Il codice web.config seguente rimuove il prefisso:
<configuration>
<configSections>
<section name="configBuilders"
type="System.Configuration.ConfigurationBuildersSection,
System.Configuration, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b03f5f7f11d50a3a"
restartOnExternalChanges="false" requirePermission="false" />
</configSections>
<configBuilders>
<builders>
<add name="AS_Environment" mode="Greedy" prefix="AppSetting_"
stripPrefix="true"
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment,
Version=1.0.0.0, Culture=neutral" />
<add name="CS_Environment" mode="Greedy" prefix="ConnStr_"
stripPrefix="true"
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment,
Version=1.0.0.0, Culture=neutral" />
</builders>
</configBuilders>
<appSettings configBuilders="AS_Environment">
<add key="ServiceID" value="ServiceID value from web.config" />
<add key="default" value="AppSetting_default value from web.config" />
</appSettings>
<connectionStrings configBuilders="CS_Environment">
<add name="default" connectionString="Data Source=web.config/mydb.db" />
</connectionStrings>
Nel file web.config precedente, la chiave è presente sia in <appSettings/> che in <connectionStrings/>.
L'immagine seguente mostra le chiavi/valori <appSettings/> e <connectionStrings/> del file web.config precedente impostato nell'editor dell'ambiente.
Il codice seguente legge le chiavi/valori <appSettings/> e <connectionStrings/> contenuti nel file web.config precedente.
public partial class About2 : Page
{
public string ServiceID { get; set; }
public string AppSetting_default { get; set; }
public string ConString { get; set; }
protected void Page_Load(object sender, EventArgs e)
{
ServiceID = ConfigurationManager.AppSettings["ServiceID"];
AppSetting_default = ConfigurationManager.AppSettings["default"];
ConString = ConfigurationManager.ConnectionStrings["default"]
?.ConnectionString;
}
}
Il codice precedente imposta i valori della proprietà su:
- I valori nel file web.config se le chiavi non sono impostate nelle variabili di ambiente.
- Valori della variabile di ambiente, se impostata.
Ad esempio, usando il file web.config precedente, le chiavi/valori nell'immagine dell'editor dell'ambiente precedente e il codice precedente, vengono impostati i valori seguenti:
| Chiave | valore |
|---|---|
| ServiceID | AppSetting_ServiceID dalle variabili di ambiente |
| impostazione predefinita | Valore predefinito di AppSetting_default da env |
| impostazione predefinita | ConnStr_valore predefinito da ambiente |
tokenPattern
tokenPattern: una stringa, per impostazione predefinita @"\$\{(\w+)\}"
Il comportamento dei Expand costruttori cerca nel codice XML non elaborato i token simili a ${token}. La ricerca viene eseguita con l'espressione @"\$\{(\w+)\}"regolare predefinita . Il set di caratteri che corrisponde a \w è più rigoroso di quanto consentito da XML e da molte fonti di configurazione. Utilizzare tokenPattern quando sono richiesti più caratteri di @"\$\{(\w+)\}" nel nome del token.
tokenPattern:Corda:
- Consente agli sviluppatori di modificare la regex utilizzata per la corrispondenza dei token.
- Non viene eseguita alcuna convalida per assicurarsi che sia un'espressione regolare ben formata e non pericolosa.
- Deve contenere un gruppo di acquisizione. L'intera espressione regolare deve corrispondere all'intero token. La prima cattura deve essere il nome del token da individuare nella fonte di configurazione.
Generatori di configurazioni in Microsoft.Configuration.ConfigurationBuilders
EnvironmentConfigBuilder
<add name="Environment"
[mode|prefix|stripPrefix|tokenPattern]
type="Microsoft.Configuration.ConfigurationBuilders.EnvironmentConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Environment" />
- È il più semplice dei generatori di configurazione.
- Legge i valori dall'ambiente.
- Non sono disponibili opzioni di configurazione aggiuntive.
- Il valore dell'attributo
nameè arbitrario.
Nota: in un ambiente contenitore Windows, le variabili impostate in fase di esecuzione vengono inserite solo nell'ambiente del processo EntryPoint. Le app eseguite come servizio o un processo non EntryPoint non prelevano queste variabili, a meno che non vengano inserite in altro modo tramite un meccanismo nel contenitore. Per i contenitori basati su IIS/ASP.NET, la versione corrente di ServiceMonitor.exe gestisce questo solo in DefaultAppPool. Altre varianti di contenitore basate su Windows potrebbero dover sviluppare il proprio meccanismo di inserimento per i processi non EntryPoint.
UserSecretsConfigBuilder
Avviso
Non archiviare mai password, stringa di connessione sensibili o altri dati sensibili nel codice sorgente. I segreti di produzione non devono essere usati per lo sviluppo o il test.
<add name="UserSecrets"
[mode|prefix|stripPrefix|tokenPattern]
(userSecretsId="{secret string, typically a GUID}" | userSecretsFile="~\secrets.file")
[optional="true"]
type="Microsoft.Configuration.ConfigurationBuilders.UserSecretsConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.UserSecrets" />
Nel codice XML precedente, il percorso userSecretsFile può usare ~/ o ~\. Ad esempio, il percorso può essere scritto come userSecretsFile="~/secrets.file. Per altre informazioni, vedere la classe ConfigurationBuilders Utils .
Questo generatore di configurazione offre una funzionalità simile a ASP.NET Core Secret Manager.
È possibile usare UserSecretsConfigBuilder nei progetti .NET Framework, ma è necessario specificare un file di segreti. In alternativa, è possibile definire la proprietà UserSecretsId nel file di progetto e creare il file grezzo dei segreti nel percorso giusto per la lettura. Per evitare dipendenze esterne dal progetto, il file segreto è formattato in formato XML. La formattazione XML è un dettaglio di implementazione e il formato non ci si dovrebbe fare affidamento. Se è necessario condividere un file secrets.json con i progetti .NET Core, è consigliabile usare SimpleJsonConfigBuilder. Anche il SimpleJsonConfigBuilder formato per .NET Core deve essere considerato un dettaglio di implementazione soggetto a modifiche.
Attributi di configurazione per UserSecretsConfigBuilder:
-
userSecretsId- Questo è il metodo preferito per identificare un file di segreti XML. Funziona in modo simile a .NET Core, che usa unaUserSecretsIdproprietà del progetto per archiviare questo identificatore. La stringa deve essere univoca, non deve essere un GUID. Con questo attributo, cerca in un percorso locale noto (%APPDATA%\Microsoft\UserSecrets\<UserSecrets Id>\secrets.xml) un file delle credenziali appartenente a questo identificatore. -
userSecretsFile- Attributo facoltativo che specifica il file contenente i segreti. Il~carattere può essere usato all'inizio per fare riferimento alla radice dell'applicazione. Questo attributo o l'attributouserSecretsIdè obbligatorio. Se vengono specificati entrambi,userSecretsFileha la precedenza. -
optional: valore booleano, valoretruepredefinito: impedisce un'eccezione se non è possibile trovare il file dei segreti. - Il valore dell'attributo
nameè arbitrario.
Il file dei segreti ha il formato seguente:
<?xml version="1.0" encoding="utf-8" ?>
<root>
<secrets ver="1.0">
<secret name="secret key name" value="secret value" />
</secrets>
</root>
AzureKeyVaultConfigBuilder
<add name="AzureKeyVault"
[mode|prefix|stripPrefix|tokenPattern]
(vaultName="MyVaultName" |
uri="https:/MyVaultName.vault.azure.net")
[version="secrets version"]
[preloadSecretNames="true"]
type="Microsoft.Configuration.ConfigurationBuilders.AzureKeyVaultConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Azure" />
AzureKeyVaultConfigBuilder legge i valori archiviati nel Key Vault di Azure.
vaultName è obbligatorio (il nome dell'archivio sicuro o un URI per l'archivio). Gli altri attributi consentono di controllare a quale vault connettersi, ma sono necessari solo se l'applicazione non è in esecuzione in un ambiente che funziona con Microsoft.Azure.Services.AppAuthentication. La libreria di autenticazione dei servizi di Azure viene usata per raccogliere automaticamente le informazioni di connessione dall'ambiente di esecuzione, se possibile. È possibile sostituire la selezione automatica delle informazioni di connessione fornendo una stringa di connessione.
-
vaultName- Obbligatorio seurinon è fornito. Specifica il nome del vault nella sottoscrizione di Azure da cui leggere coppie chiave/valore. -
uri- Si connette ad altri provider di Key Vault con il valore specificatouri. Se non specificato, Azure (vaultName) è il provider del vault. -
version- Azure Key Vault offre una funzionalità di controllo delle versioni per i segreti. Seversionviene specificato, il generatore recupera solo i segreti corrispondenti a questa versione. -
preloadSecretNames- Per impostazione predefinita, questo generatore interroga tutti i nomi delle chiavi nel Key Vault quando viene inizializzato. Per impedire la lettura di tutti i valori di chiave, impostare questo attributo sufalse. L'impostazione di questa opzione sufalselegge i segreti uno alla volta. Leggere i segreti uno alla volta può essere utile se il caveau consente l'accesso "Get", ma non "List". Nota: quando si usaGreedyla modalità,preloadSecretNamesdeve esseretrue(impostazione predefinita).
KeyPerFileConfigBuilder
<add name="KeyPerFile"
[mode|prefix|stripPrefix|tokenPattern]
(directoryPath="PathToSourceDirectory")
[ignorePrefix="ignore."]
[keyDelimiter=":"]
[optional="false"]
type="Microsoft.Configuration.ConfigurationBuilders.KeyPerFileConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.KeyPerFile" />
KeyPerFileConfigBuilder è un generatore di configurazione di base che usa i file di una directory come origine dei valori. Il nome di un file è la chiave e il contenuto è il valore. Questo generatore di configurazione può essere utile quando viene eseguito in un ambiente contenitore orchestrato. I sistemi come Docker Swarm e Kubernetes forniscono secrets ai contenitori Windows orchestrati in questo formato chiave-per-file.
Dettagli attributo:
-
directoryPath- Obbligatorio. Specifica un percorso in cui cercare i valori. Per impostazione predefinita, Docker per i segreti di Windows vengono archiviati nella directory C:\ProgramData\Docker\secrets . -
ignorePrefix- I file che iniziano con questo prefisso vengono esclusi. Il valore predefinito è "ignore". -
keyDelimiter- Il valore predefinito ènull. Se specificato, il generatore di configurazione attraversa più livelli della directory, creando nomi di chiave con questo delimitatore. Se questo valore ènull, il generatore di configurazione esamina solo il livello superiore della directory. -
optional- Il valore predefinito èfalse. Specifica se il generatore di configurazione deve causare errori se la directory di origine non esiste.
SimpleJsonConfigBuilder
Avviso
Non archiviare mai password, stringa di connessione sensibili o altri dati sensibili nel codice sorgente. I segreti di produzione non devono essere usati per lo sviluppo o il test.
<add name="SimpleJson"
[mode|prefix|stripPrefix|tokenPattern]
jsonFile="~\config.json"
[optional="true"]
[jsonMode="(Flat|Sectional)"]
type="Microsoft.Configuration.ConfigurationBuilders.SimpleJsonConfigBuilder,
Microsoft.Configuration.ConfigurationBuilders.Json" />
I progetti .NET Core usano spesso file JSON per la configurazione. Il generatore SimpleJsonConfigBuilder consente l'uso di file JSON .NET Core in .NET Framework. Questo generatore di configurazione fornisce un mapping di base da un'origine chiave/valore piatta verso ambiti specifici della configurazione chiave/valore di .NET Framework. Questo generatore di configurazione non fornisce configurazioni gerarchiche. Il file di backup JSON è simile a un dizionario, non a un oggetto gerarchico complesso. È possibile usare un file gerarchico a più livelli. Questo provider flatten aggiunge il nome della proprietà a ogni livello usando : come separatore.
Dettagli attributo:
jsonFile- Obbligatorio. Specifica il file JSON da cui leggere. Il~carattere può essere usato all'inizio per fare riferimento alla radice dell'app.optional- Valore booleano, il valore predefinito ètrue. Impedisce la generazione di eccezioni se non è possibile trovare il file JSON.jsonMode-[Flat|Sectional].Flatè l'impostazione predefinita. QuandojsonModeèFlat, il file JSON è un'unica origine chiave/valore piatta.EnvironmentConfigBuildereAzureKeyVaultConfigBuildersono anche singole origini chiave/valore flat. Quando ilSimpleJsonConfigBuilderè configurato in modalitàSectional- Il file JSON è concettualmente diviso solo al livello superiore in più dizionari.
- Ogni dizionario viene applicato esclusivamente alla sezione di configurazione corrispondente al nome della proprietà di primo livello associato. Ad esempio:
{
"appSettings" : {
"setting1" : "value1",
"setting2" : "value2",
"complex" : {
"setting1" : "complex:value1",
"setting2" : "complex:value2",
}
}
}
Ordine dei generatori di configurazione
Consulta Ordine di esecuzione di ConfigurationBuilders nel repository GitHub aspnet/MicrosoftConfigurationBuilders.
Implementazione di un generatore di configurazione chiave/valore personalizzato
Se i generatori di configurazione non soddisfano le proprie esigenze, è possibile scriverne uno personalizzato. La KeyValueConfigBuilder classe base gestisce le modalità di sostituzione e la maggior parte dei problemi di prefisso. Un progetto di implementazione deve solo:
- Ereditare dalla classe base e implementare una fonte di base di coppie chiave/valore tramite
GetValueeGetAllValues: - Aggiungere Microsoft.Configuration.ConfigurationBuilders.Base al progetto.
using Microsoft.Configuration.ConfigurationBuilders;
using System.Collections.Generic;
public class MyCustomConfigBuilder : KeyValueConfigBuilder
{
public override string GetValue(string key)
{
// Key lookup should be case-insensitive, because most key/value collections in
// .NET Framework config sections are case-insensitive.
return "Value for given key, or null.";
}
public override ICollection<KeyValuePair<string, string>> GetAllValues(string prefix)
{
// Populate the return collection.
return new Dictionary<string, string>() { { "one", "1" }, { "two", "2" } };
}
}
La KeyValueConfigBuilder classe base fornisce gran parte del comportamento di lavoro e coerente tra i generatori di configurazioni chiave/valore.