Anpassen von Eigenschaftsnamen und -werten mit System.Text.Json

Standardmäßig bleiben Eigenschaftsnamen und Wörterbuchschlüssel in der JSON-Ausgabe unverändert, einschließlich der Groß-/Kleinschreibung. Enumerationswerte werden als Zahlen dargestellt. Und Eigenschaften werden in der Reihenfolge serialisiert, in der sie definiert sind. Sie können diese Verhaltensweisen jedoch wie folgt anpassen:

  • Geben Sie bestimmte serialisierte Eigenschaftennamen an.
  • Verwenden Sie eine integrierte Benennungsrichtlinie, z. B. camelCase, snake_case oder Kebab-Fall, für Eigenschaftsnamen und Wörterbuchschlüssel.
  • Verwenden Sie eine benutzerdefinierte Benennungsrichtlinie für Eigenschaftennamen und Wörterbuchschlüssel.
  • Serialisieren Sie Enumerationswerte als Zeichenfolgen mit oder ohne Benennungsrichtlinie.
  • Konfiguriere Sie die Reihenfolge serialisierter Eigenschaften.

Hinweis

Die Standardbenennungsrichtlinie des Webs ist camelCase.

Für andere Szenarien, die eine besondere Behandlung von JSON-Eigenschaftsnamen und -werten erfordern, können Sie benutzerdefinierte Konverter implementieren.

Anpassen einzelner Eigenschaftsnamen

Um den Namen einzelner Eigenschaften festzulegen, verwenden Sie das Attribut [JsonPropertyName].

Hier finden Sie einen zu serialisierenden Beispieltyp und die daraus resultierende JSON-Ausgabe:

public class WeatherForecastWithPropertyNameAttribute
{
    public DateTimeOffset Date { get; set; }
    public int TemperatureCelsius { get; set; }
    public string? Summary { get; set; }
    [JsonPropertyName("Wind")]
    public int WindSpeed { get; set; }
}
Public Class WeatherForecastWithPropertyNameAttribute
    Public Property [Date] As DateTimeOffset
    Public Property TemperatureCelsius As Integer
    Public Property Summary As String

    <JsonPropertyName("Wind")>
    Public Property WindSpeed As Integer

End Class
{
  "Date": "2019-08-01T00:00:00-07:00",
  "TemperatureCelsius": 25,
  "Summary": "Hot",
  "Wind": 35
}

Der über dieses Attribut festgelegte Eigenschaftsname:

Verwenden Sie eine integrierte Benennungsrichtlinie

In der folgenden Tabelle sind die integrierten Benennungsrichtlinien und ihre Auswirkungen auf Eigenschaftennamen aufgeführt.

Benennungsrichtlinie Beschreibung Ursprünglicher Eigenschaftsname Konvertierter Eigenschaftsname
CamelCase Erstes Wort beginnt mit einem Kleinbuchstaben.
Aufeinander folgende Wörter beginnen mit einem Großbuchstaben.
TempCelsius tempCelsius
KebabCaseLower* Wörter werden durch Bindestriche getrennt.
Alle Zeichen sind Kleinbuchstaben.
TempCelsius temp-celsius
KebabCaseUpper* Wörter werden durch Bindestriche getrennt.
Alle Zeichen sind Großbuchstaben.
TempCelsius TEMP-CELSIUS
SnakeCaseLower* Wörter werden durch Unterstriche getrennt.
Alle Zeichen sind Kleinbuchstaben.
TempCelsius temp_celsius
SnakeCaseUpper* Wörter werden durch Unterstriche getrennt.
Alle Zeichen sind Großbuchstaben.
TempCelsius TEMP_CELSIUS

(Verfügbar in .NET 8 und höheren Versionen.)

Das folgende Beispiel zeigt, wie Sie camelCase für alle JSON-Eigenschaftsnamen verwenden, indem Sie JsonSerializerOptions.PropertyNamingPolicy für JsonNamingPolicy.CamelCase festlegen:

var serializeOptions = new JsonSerializerOptions
{
    PropertyNamingPolicy = JsonNamingPolicy.CamelCase,
    WriteIndented = true
};
jsonString = JsonSerializer.Serialize(weatherForecast, serializeOptions);
Dim serializeOptions As JsonSerializerOptions = New JsonSerializerOptions With {
    .PropertyNamingPolicy = JsonNamingPolicy.CamelCase,
    .WriteIndented = True
}
jsonString = JsonSerializer.Serialize(weatherForecast, serializeOptions)

Hier finden Sie eine zu serialisierenden Beispielklasse und die JSON-Ausgabe:

public class WeatherForecastWithPropertyNameAttribute
{
    public DateTimeOffset Date { get; set; }
    public int TemperatureCelsius { get; set; }
    public string? Summary { get; set; }
    [JsonPropertyName("Wind")]
    public int WindSpeed { get; set; }
}
Public Class WeatherForecastWithPropertyNameAttribute
    Public Property [Date] As DateTimeOffset
    Public Property TemperatureCelsius As Integer
    Public Property Summary As String

    <JsonPropertyName("Wind")>
    Public Property WindSpeed As Integer

End Class
{
  "date": "2019-08-01T00:00:00-07:00",
  "temperatureCelsius": 25,
  "summary": "Hot",
  "Wind": 35
}

Die Benennungsrichtlinie:

  • Gilt für Serialisierung und Deserialisierung.
  • Wird von [JsonPropertyName]-Attributen außer Kraft gesetzt. Aus diesem Grund ist der JSON-Eigenschaftsname Wind im Beispiel nicht in Camel-Case-Schreibweise.

Hinweis

Keiner der integrierten Benennungsrichtlinien unterstützt Briefe, die Ersatzpaare sind. Weitere Informationen finden Sie unter Dotnet-/Runtime-Problem 90352.

Verwenden einer benutzerdefinierten Benennungsrichtlinie für JSON-Eigenschaften

Um eine benutzerdefinierte Benennungsrichtlinie für JSON-Eigenschaften zu verwenden, erstellen Sie eine Klasse, die von JsonNamingPolicy abgeleitet ist, und setzen Sie die ConvertName-Methode außer Kraft, wie im folgenden Beispiel gezeigt:

using System.Text.Json;

namespace SystemTextJsonSamples
{
    public class UpperCaseNamingPolicy : JsonNamingPolicy
    {
        public override string ConvertName(string name) =>
            name.ToUpper();
    }
}
Imports System.Text.Json

Namespace SystemTextJsonSamples

    Public Class UpperCaseNamingPolicy
        Inherits JsonNamingPolicy

        Public Overrides Function ConvertName(name As String) As String
            Return name.ToUpper()
        End Function

    End Class

End Namespace

Legen Sie dann die JsonSerializerOptions.PropertyNamingPolicy-Eigenschaft auf eine Instanz Ihre Benennungsrichtlinienklasse fest:

var options = new JsonSerializerOptions
{
    PropertyNamingPolicy = new UpperCaseNamingPolicy(),
    WriteIndented = true
};
jsonString = JsonSerializer.Serialize(weatherForecast, options);
Dim options As JsonSerializerOptions = New JsonSerializerOptions With {
    .PropertyNamingPolicy = New UpperCaseNamingPolicy,
    .WriteIndented = True
}
jsonString = JsonSerializer.Serialize(weatherForecast1, options)

Hier finden Sie eine zu serialisierenden Beispielklasse und die JSON-Ausgabe:

public class WeatherForecastWithPropertyNameAttribute
{
    public DateTimeOffset Date { get; set; }
    public int TemperatureCelsius { get; set; }
    public string? Summary { get; set; }
    [JsonPropertyName("Wind")]
    public int WindSpeed { get; set; }
}
Public Class WeatherForecastWithPropertyNameAttribute
    Public Property [Date] As DateTimeOffset
    Public Property TemperatureCelsius As Integer
    Public Property Summary As String

    <JsonPropertyName("Wind")>
    Public Property WindSpeed As Integer

End Class
{
  "DATE": "2019-08-01T00:00:00-07:00",
  "TEMPERATURECELSIUS": 25,
  "SUMMARY": "Hot",
  "Wind": 35
}

Die Benennungsrichtlinie für JSON-Eigenschaften:

  • Gilt für Serialisierung und Deserialisierung.
  • Wird von [JsonPropertyName]-Attributen außer Kraft gesetzt. Aus diesem Grund ist der JSON-Eigenschaftsname Wind im Beispiel nicht in Großbuchstaben.

Verwenden einer Benennungsrichtlinie für Wörterbuchschlüssel

Wenn eine Eigenschaft eines zu serialisierenden Objekts vom Typ Dictionary<string,TValue> ist, können die string-Schlüssel mithilfe einer Benennungsrichtlinie konvertiert werden, z. B. camelCase. Legen Sie dazu JsonSerializerOptions.DictionaryKeyPolicy auf die gewünschte Benennungsrichtlinie fest. Im folgenden Beispiel wird die CamelCase-Benennungsrichtlinie verwendet:

var options = new JsonSerializerOptions
{
    DictionaryKeyPolicy = JsonNamingPolicy.CamelCase,
    WriteIndented = true
};
jsonString = JsonSerializer.Serialize(weatherForecast, options);
Dim options As JsonSerializerOptions = New JsonSerializerOptions With {
    .DictionaryKeyPolicy = JsonNamingPolicy.CamelCase,
    .WriteIndented = True
}
jsonString = JsonSerializer.Serialize(weatherForecast, options)

Das Serialisieren eines Objekts mit einem Wörterbuch namens TemperatureRanges, das die Schlüssel-Wert-Paare "ColdMinTemp", 20 und "HotMinTemp", 40 enthält, würde zu einer JSON-Ausgabe wie im folgenden Beispiel führen:

{
  "Date": "2019-08-01T00:00:00-07:00",
  "TemperatureCelsius": 25,
  "Summary": "Hot",
  "TemperatureRanges": {
    "coldMinTemp": 20,
    "hotMinTemp": 40
  }
}

Benennungsrichtlinien für Wörterbuchschlüssel gelten nur für die Serialisierung. Wenn Sie ein Wörterbuch deserialisieren, stimmen die Schlüssel auch dann mit der JSON-Datei überein, wenn Sie JsonSerializerOptions.DictionaryKeyPolicy für eine nicht standardmäßige Benennungsrichtlinie festlegen.

Enumerationen als Zeichenfolgen

Standardmäßig werden Enumerationen als Zahlen serialisiert. Um Enumerationen als Zeichenfolgen zu serialisieren, verwenden Sie den JsonStringEnumConverter- oder JsonStringEnumConverter<TEnum>-Konverter. Nur JsonStringEnumConverter<TEnum> wird von der nativen AOT-Laufzeit unterstützt.

Standardmäßig werden Enumerationen als Zahlen serialisiert. Um Enumerationen als Zeichenfolgen zu serialisieren, verwenden Sie den JsonStringEnumConverter-Konverter.

Angenommen, Sie müssen die folgende Klasse serialisieren, die über eine Enumeration verfügt:

public class WeatherForecastWithEnum
{
    public DateTimeOffset Date { get; set; }
    public int TemperatureCelsius { get; set; }
    public Summary? Summary { get; set; }
}

public enum Summary
{
    Cold, Cool, Warm, Hot
}
Public Class WeatherForecastWithEnum
    Public Property [Date] As DateTimeOffset
    Public Property TemperatureCelsius As Integer
    Public Property Summary As Summary
End Class

Public Enum Summary
    Cold
    Cool
    Warm
    Hot
End Enum

Wenn die Zusammenfassung Hot ist, hat das serialisierte JSON standardmäßig den numerischen Wert 3:

{
  "Date": "2019-08-01T00:00:00-07:00",
  "TemperatureCelsius": 25,
  "Summary": 3
}

Der folgende Beispielcode serialisiert die Enumerationsnamen anstelle der numerischen Werte und konvertiert die Namen in die Camel-Case-Schreibweise:

options = new JsonSerializerOptions
{
    WriteIndented = true,
    Converters =
    {
        new JsonStringEnumConverter(JsonNamingPolicy.CamelCase)
    }
};
jsonString = JsonSerializer.Serialize(weatherForecast, options);
options = New JsonSerializerOptions With {
    .WriteIndented = True
}
options.Converters.Add(New JsonStringEnumConverter(JsonNamingPolicy.CamelCase))
jsonString = JsonSerializer.Serialize(weatherForecast, options)

Das resultierende JSON sieht wie im folgenden Beispiel aus:

{
  "Date": "2019-08-01T00:00:00-07:00",
  "TemperatureCelsius": 25,
  "Summary": "hot"
}

Der integrierte JsonStringEnumConverter kann auch Zeichenfolgenwerte deserialisieren. Es funktioniert mit oder ohne eine angegebene Benennungsrichtlinie. Das folgende Beispiel zeigt die Deserialisierung mit CamelCase:

options = new JsonSerializerOptions
{
    Converters =
    {
        new JsonStringEnumConverter(JsonNamingPolicy.CamelCase)
    }
};
weatherForecast = JsonSerializer.Deserialize<WeatherForecastWithEnum>(jsonString, options)!;
options = New JsonSerializerOptions
options.Converters.Add(New JsonStringEnumConverter(JsonNamingPolicy.CamelCase))
weatherForecast = JsonSerializer.Deserialize(Of WeatherForecastWithEnum)(jsonString, options)

Sie können auch den zu verwendenden Konverter angeben, indem Sie die Enumeration mit JsonConverterAttribute markieren. Das folgende Beispiel zeigt, wie Sie die JsonStringEnumConverter<TEnum> (in .NET 8 und höheren Versionen verfügbar) mithilfe des JsonConverterAttribute-Attributs angeben. Angenommen, Sie müssen die folgende Klasse serialisieren, die über eine Enumeration verfügt:

public class WeatherForecastWithPrecipEnum
{
    public DateTimeOffset Date { get; set; }
    public int TemperatureCelsius { get; set; }
    public Precipitation? Precipitation { get; set; }
}

[JsonConverter(typeof(JsonStringEnumConverter<Precipitation>))]
public enum Precipitation
{
    Drizzle, Rain, Sleet, Hail, Snow
}

Im folgenden Beispielcode werden die Enumerationsnamen anstelle der numerischen Werte serialisiert:

var options = new JsonSerializerOptions
{
    WriteIndented = true,
};
jsonString = JsonSerializer.Serialize(weatherForecast, options);

Das resultierende JSON sieht wie im folgenden Beispiel aus:

{
  "Date": "2019-08-01T00:00:00-07:00",
  "TemperatureCelsius": 25,
  "Precipitation": "Sleet"
}

Informationen zum Verwenden des Konverters mit der Quellgenerierung finden Sie unter Serialisieren von Enumerationsfeldern als Zeichenfolgen.

Konfigurieren der Reihenfolge serialisierter Eigenschaften

Standardmäßig werden Eigenschaften in der Reihenfolge serialisiert, in der sie in ihrer Klasse definiert sind. Mit dem [JsonPropertyOrder]-Attribut können Sie die Reihenfolge der Eigenschaften in der JSON-Ausgabe der Serialisierung angeben. Der Standardwert der Order-Eigenschaft ist Null. Legen Sie Order auf eine positive Zahl fest, um eine Eigenschaft nach Eigenschaften mit dem Standardwert zu positionieren. Durch einen negativen Order-Wert wird eine Eigenschaft vor Eigenschaften mit dem Standardwert positioniert. Eigenschaften werden in aufsteigender Reihenfolge des Order-Werts ausgegeben. Hier sehen Sie ein Beispiel:

using System.Text.Json;
using System.Text.Json.Serialization;

namespace PropertyOrder
{
    public class WeatherForecast
    {
        [JsonPropertyOrder(-5)]
        public DateTime Date { get; set; }
        public int TemperatureC { get; set; }
        [JsonPropertyOrder(-2)]
        public int TemperatureF { get; set; }
        [JsonPropertyOrder(5)]
        public string? Summary { get; set; }
        [JsonPropertyOrder(2)]
        public int WindSpeed { get; set; }
    }

    public class Program
    {
        public static void Main()
        {
            var weatherForecast = new WeatherForecast
            {
                Date = DateTime.Parse("2019-08-01"),
                TemperatureC = 25,
                TemperatureF = 25,
                Summary = "Hot",
                WindSpeed = 10
            };

            var options = new JsonSerializerOptions { WriteIndented = true };
            string jsonString = JsonSerializer.Serialize(weatherForecast, options);
            Console.WriteLine(jsonString);
        }
    }
}
// output:
//{
//  "Date": "2019-08-01T00:00:00",
//  "TemperatureF": 25,
//  "TemperatureC": 25,
//  "WindSpeed": 10,
//  "Summary": "Hot"
//}

Weitere Informationen