wake-up-neo.com

Wie lade ich appsetting.json in das Dictionary in .NET Core?

Ich bin vertraut mit dem Laden eines appsettings.json-Abschnitts in ein stark typisiertes Objekt in .NET Core startup.cs. Zum Beispiel:

public class CustomSection 
{
   public int A {get;set;}
   public int B {get;set;}
}

//In Startup.cs
services.Configure<CustomSection>(Configuration.GetSection("CustomSection"));

//Inject an IOptions instance
public HomeController(IOptions<CustomSection> options) 
{
    var settings = options.Value;
}

Ich habe einen Bereich appsettings.json, dessen Schlüssel-/Wert-Paare in Anzahl und Namen im Laufe der Zeit variieren. Daher ist es nicht praktikabel, Eigenschaftsnamen in einer Klasse fest zu codieren, da neue Schlüssel/Wert-Paare eine Codeänderung in der Klasse erfordern würden. Eine kleine Auswahl einiger Schlüssel/Wert-Paare:

"MobileConfigInfo": {
    "appointment-confirmed": "We've booked your appointment. See you soon!",
    "appointments-book": "New Appointment",
    "appointments-null": "We could not locate any upcoming appointments for you.",
    "availability-null": "Sorry, there are no available times on this date. Please try another."
}

Gibt es eine Möglichkeit, diese Daten in ein MobileConfigInfo Dictionary-Objekt zu laden und dann das IOptions-Muster zu verwenden, um MobileConfigInfo in eine Steuerung einzuspeisen?

15
ChrisP

Sie können Configuration.Bind(settings); in der startup.cs-Klasse verwenden

Und Ihre Einstellungsklasse wird wie sein 

public class AppSettings
{
    public Dictionary<string, string> MobileConfigInfo
    {
        get;
        set;
    }
}

Ich hoffe es hilft!

16
Hung Cao

Gehen Sie mit diesem Strukturformat:

"MobileConfigInfo": {
    "Values": {
       "appointment-confirmed": "We've booked your appointment. See you soon!",
       "appointments-book": "New Appointment",
       "appointments-null": "We could not locate any upcoming appointments for you.",
       "availability-null": "Sorry, there are no available times on this date. Please try another."
 }
}

Lass deine Setting-Klasse so aussehen:

public class CustomSection 
{
   public Dictionary<string, string> Values {get;set;}
}

dann mach das

services.Configure<CustomSection>((settings) =>
{
     Configuration.GetSection("MobileConfigInfo").Bind(settings);
});
13
code5

Für andere, die es in ein Dictionary konvertieren wollen, 

beispielabschnitt in appsettings.json

"MailSettings": {
    "Server": "http://mail.mydomain.com"        
    "Port": "25",
    "From": "[email protected]"
 }

Folgender Code sollte in die Startdatei> ConfigureServices-Methode eingefügt werden:

public static Dictionary<string, object> MailSettings { get; private set; }

public void ConfigureServices(IServiceCollection services)
{
    //ConfigureServices code......

    MailSettings = 
        Configuration.GetSection("MailSettings").GetChildren()
        .Select(item => new KeyValuePair<string, string>(item.Key, item.Value))
        .ToDictionary(x => x.Key, x => x.Value);
}

Jetzt können Sie von überall auf das Wörterbuch zugreifen:

string mailServer = Startup.MailSettings["Server"];

Ein Nachteil ist, dass alle Werte als Zeichenfolgen abgerufen werden. Wenn Sie einen anderen Typ ausprobieren, ist der Wert null.

11
Amro

Ich glaube, Sie können den folgenden Code verwenden:

var config =  Configuration.GetSection("MobileConfigInfo").Get<Dictionary<string, string>>(); 
2
macpak

Für einfache Anwendungen (vielleicht Microservice-Anwendungen) können Sie es einfach als Einzelcode Dictionary<string, string> hinzufügen und es dann an jeder beliebigen Stelle einfügen:

var mobileConfig = Configuration.GetSection("MobileConfigInfo")
                    .GetChildren().ToDictionary(x => x.Key, x => x.Value);

services.AddSingleton(mobileConfig);

Und die Verwendung:

public class MyDependantClass
{
    private readonly Dictionary<string, string> _mobileConfig;

    public MyDependantClass(Dictionary<string, string> mobileConfig)
    {
        _mobileConfig = mobileConfig;
    }

    // Use your mobile config here
}
2
ste-fu

Als Beispiel für eine komplexere Bindung in ASP.Net Core 2.1; Ich fand die Verwendung der ConfigurationBuilder.Get<T>()-Methode viel einfacher, mit der Dokumentation zu arbeiten.

ASP.NET Core 1.1 und höher kann Get verwenden, das mit ganzen Abschnitten funktioniert. Holen Sie sich bequemer als mit Bind.

Ich habe die Konfiguration in meiner Startup-Methode gebunden.

private Config Config { get; }

public Startup(IConfiguration Configuration)
{
    Config = Configuration.Get<Config>();
}

Dies bindet die appsettings-Datei:

{
    "ConnectionStrings": {
        "Accounts": "Server=localhost;Database=Accounts;Trusted_Connection=True;",
        "test": "Server=localhost;Database=test;Trusted_Connection=True;",
        "Client": "Server=localhost;Database={DYNAMICALLY_BOUND_CONTEXT};Trusted_Connection=True;",
        "Support": "Server=localhost;Database=Support;Trusted_Connection=True;"
    },
    "Logging": {
        "IncludeScopes": false,
        "LogLevel": {
            "Default": "Debug",
            "System": "Information",
            "Microsoft": "Information"
        }
    },
    "Plugins": {
        "SMS": {
            "RouteMobile": {
                "Scheme": "https",
                "Host": "remote.Host",
                "Port": 84567,
                "Path": "/bulksms",
                "Username": "username",
                "Password": "password",
                "Source": "CompanyName",
                "DeliveryReporting": true,
                "MessageType": "Unicode"
            }
        },
        "SMTP": {
            "GenericSmtp": {
                "Scheme": "https",
                "Host": "mail.Host",
                "Port": 25,
                "EnableSsl": true,
                "Username": "[email protected]",
                "Password": "password",
                "DefaultSender": "[email protected]"
            }
        }
    }
}

In diese Konfigurationsstruktur:

[DataContract]
public class Config
{
    [DataMember]
    public Dictionary<string, string> ConnectionStrings { get; set; }
    [DataMember]
    public PluginCollection Plugins { get; set; }
}

[DataContract]
public class PluginCollection
{
    [DataMember]
    public Dictionary<string, SmsConfiguration> Sms { get; set; }
    [DataMember]
    public Dictionary<string, EmailConfiguration> Smtp { get; set; }
}

[DataContract]
public class SmsConfiguration
{
    [DataMember]
    public string Scheme { get; set; }
    [DataMember]
    public string Host { get; set; }
    [DataMember]
    public int Port { get; set; }
    [DataMember]
    public string Path { get; set; }
    [DataMember]
    public string Username { get; set; }
    [DataMember]
    public string Password { get; set; }
    [DataMember]
    public string Source { get; set; }
    [DataMember]
    public bool DeliveryReporting { get; set; }
    [DataMember]
    public string Encoding { get; set; }
}

[DataContract]
public class EmailConfiguration
{
    [DataMember]
    public string Scheme { get; set; }
    [DataMember]
    public string Host { get; set; }
    [DataMember]
    public int Port { get; set; }
    [DataMember]
    public string Path { get; set; }
    [DataMember]
    public string Username { get; set; }
    [DataMember]
    public string Password { get; set; }
    [DataMember]
    public string DefaultSender { get; set; }
    [DataMember]
    public bool EnableSsl { get; set; }
}
1
derpasaurus

Bei weitem die einfachste Methode wäre, Ihre Konfigurationsklasse so zu definieren, dass sie von dem Dictionary-Typ erbt, den Sie unterstützen möchten.

public class MobileConfigInfo:Dictionary<string, string>{
}

Dann stimmen Sie beim Starten und bei der Abhängigkeitsinjektion genauso überein wie bei jedem anderen Konfigurationstyp.

0
Jeremy Lakeman

Ich benutze den Weg unten:

appsettings.json:

  "services": {
      "user-service": "http://user-service:5000/",
      "app-service": "http://app-service:5000/"
  } 

startup.cs:

  services.Configure<Dictionary<string, string>>(Configuration.GetSection("services"));

Verwendungszweck:

private readonly Dictionary<string, string> _services;
public YourConstructor(IOptions<Dictionary<string, string>> servicesAccessor)
{
    _services = servicesAccessor.Value;
}
0
ErikXu