Brongeneratie gebruiken in System.Text.Json
Brongeneratie System.Text.Json is beschikbaar in .NET 6 en nieuwere versies. Wanneer deze wordt gebruikt in een app, moet de taalversie van de app C# 9.0 of hoger zijn. In dit artikel wordt beschreven hoe u serialisatie met brongeneratie kunt gebruiken in uw apps.
Zie de modi voor het genereren van bronnen voor informatie over de verschillende modi voor het genereren van bronnen.
Standaardinstellingen voor het genereren van bronnen gebruiken
Brongeneratie gebruiken met alle standaardinstellingen (beide modi, standaardopties):
Maak een gedeeltelijke klasse die is afgeleid van JsonSerializerContext.
Geef het type op dat u wilt serialiseren of deserialiseren door deze toe te passen op JsonSerializableAttribute de contextklasse.
Roep een methode aan JsonSerializer die:
- Neemt een JsonTypeInfo<T> instantie, of
- Neemt een JsonSerializerContext instantie, of
- Neemt een JsonSerializerOptions exemplaar en u hebt de eigenschap ervan ingesteld JsonSerializerOptions.TypeInfoResolver op de
Default
eigenschap van het contexttype (alleen.NET 7 en hoger).
Standaard worden beide brongeneratiemodi gebruikt als u er geen opgeeft. Zie De modus voor het genereren van bronnen later in dit artikel opgeven voor informatie over het opgeven van de modus die moet worden gebruikt.
Dit is het type dat wordt gebruikt in de volgende voorbeelden:
public class WeatherForecast
{
public DateTime Date { get; set; }
public int TemperatureCelsius { get; set; }
public string? Summary { get; set; }
}
Dit is de contextklasse die is geconfigureerd om brongeneratie uit te voeren voor de voorgaande WeatherForecast
klasse:
[JsonSourceGenerationOptions(WriteIndented = true)]
[JsonSerializable(typeof(WeatherForecast))]
internal partial class SourceGenerationContext : JsonSerializerContext
{
}
De typen WeatherForecast
leden hoeven niet expliciet met kenmerken te worden opgegeven [JsonSerializable]
. Leden die zijn gedeclareerd als object
een uitzondering op deze regel. Het runtimetype voor een lid dat moet worden opgegeven object
. Stel dat u de volgende klasse hebt:
public class WeatherForecast
{
public object? Data { get; set; }
public List<object>? DataList { get; set; }
}
En u weet dat het tijdens runtime mogelijk en int
objecten heeftboolean
:
WeatherForecast wf = new() { Data = true, DataList = new List<object> { true, 1 } };
int
Vervolgens boolean
moet deze worden gedeclareerd als[JsonSerializable]
:
[JsonSerializable(typeof(WeatherForecast))]
[JsonSerializable(typeof(bool))]
[JsonSerializable(typeof(int))]
public partial class WeatherForecastContext : JsonSerializerContext
{
}
Als u brongeneratie voor een verzameling wilt opgeven, gebruikt [JsonSerializable]
u dit met het verzamelingstype. Voorbeeld: [JsonSerializable(typeof(List<WeatherForecast>))]
.
JsonSerializer
methoden die gebruikmaken van brongeneratie
In de volgende voorbeelden biedt de statische Default
eigenschap van het contexttype een exemplaar van het contexttype met standaardopties. Het contextexemplaren biedt een WeatherForecast
eigenschap die een JsonTypeInfo<WeatherForecast>
exemplaar retourneert. U kunt een andere naam voor deze eigenschap opgeven met behulp van de TypeInfoPropertyName eigenschap van het [JsonSerializable]
kenmerk.
Voorbeelden van serialisatie
Met behulp van JsonTypeInfo<T>:
jsonString = JsonSerializer.Serialize(
weatherForecast!, SourceGenerationContext.Default.WeatherForecast);
Met behulp van JsonSerializerContext:
jsonString = JsonSerializer.Serialize(
weatherForecast, typeof(WeatherForecast), SourceGenerationContext.Default);
Met behulp van JsonSerializerOptions:
sourceGenOptions = new JsonSerializerOptions
{
TypeInfoResolver = SourceGenerationContext.Default
};
jsonString = JsonSerializer.Serialize(
weatherForecast, typeof(WeatherForecast), sourceGenOptions);
Voorbeelden van deserialisatie
Met behulp van JsonTypeInfo<T>:
weatherForecast = JsonSerializer.Deserialize<WeatherForecast>(
jsonString, SourceGenerationContext.Default.WeatherForecast);
Met behulp van JsonSerializerContext:
weatherForecast = JsonSerializer.Deserialize(
jsonString, typeof(WeatherForecast), SourceGenerationContext.Default)
as WeatherForecast;
Met behulp van JsonSerializerOptions:
var sourceGenOptions = new JsonSerializerOptions
{
TypeInfoResolver = SourceGenerationContext.Default
};
weatherForecast = JsonSerializer.Deserialize(
jsonString, typeof(WeatherForecast), sourceGenOptions)
as WeatherForecast;
Voorbeeld van het volledige programma
Hier volgen de voorgaande voorbeelden in een volledig programma:
using System.Text.Json;
using System.Text.Json.Serialization;
namespace BothModesNoOptions
{
public class WeatherForecast
{
public DateTime Date { get; set; }
public int TemperatureCelsius { get; set; }
public string? Summary { get; set; }
}
[JsonSourceGenerationOptions(WriteIndented = true)]
[JsonSerializable(typeof(WeatherForecast))]
internal partial class SourceGenerationContext : JsonSerializerContext
{
}
public class Program
{
public static void Main()
{
string jsonString = """
{
"Date": "2019-08-01T00:00:00",
"TemperatureCelsius": 25,
"Summary": "Hot"
}
""";
WeatherForecast? weatherForecast;
weatherForecast = JsonSerializer.Deserialize<WeatherForecast>(
jsonString, SourceGenerationContext.Default.WeatherForecast);
Console.WriteLine($"Date={weatherForecast?.Date}");
// output:
//Date=8/1/2019 12:00:00 AM
weatherForecast = JsonSerializer.Deserialize(
jsonString, typeof(WeatherForecast), SourceGenerationContext.Default)
as WeatherForecast;
Console.WriteLine($"Date={weatherForecast?.Date}");
// output:
//Date=8/1/2019 12:00:00 AM
var sourceGenOptions = new JsonSerializerOptions
{
TypeInfoResolver = SourceGenerationContext.Default
};
weatherForecast = JsonSerializer.Deserialize(
jsonString, typeof(WeatherForecast), sourceGenOptions)
as WeatherForecast;
Console.WriteLine($"Date={weatherForecast?.Date}");
// output:
//Date=8/1/2019 12:00:00 AM
jsonString = JsonSerializer.Serialize(
weatherForecast!, SourceGenerationContext.Default.WeatherForecast);
Console.WriteLine(jsonString);
// output:
//{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"}
jsonString = JsonSerializer.Serialize(
weatherForecast, typeof(WeatherForecast), SourceGenerationContext.Default);
Console.WriteLine(jsonString);
// output:
//{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"}
sourceGenOptions = new JsonSerializerOptions
{
TypeInfoResolver = SourceGenerationContext.Default
};
jsonString = JsonSerializer.Serialize(
weatherForecast, typeof(WeatherForecast), sourceGenOptions);
Console.WriteLine(jsonString);
// output:
//{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"}
}
}
}
Modus voor het genereren van bron opgeven
U kunt de modus op basis van metagegevens of serialisatieoptimalisatie opgeven voor een volledige context, die meerdere typen kan bevatten. U kunt ook de modus voor een afzonderlijk type opgeven. Als u beide doet, wordt de modusspecificatie voor een type wint.
- Gebruik de JsonSourceGenerationOptionsAttribute.GenerationMode eigenschap voor een volledige context.
- Gebruik de JsonSerializableAttribute.GenerationMode eigenschap voor een afzonderlijk type.
Voorbeeld van serialisatie-optimalisatiemodus (snel pad)
Voor een volledige context:
[JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Serialization)] [JsonSerializable(typeof(WeatherForecast))] internal partial class SerializeOnlyContext : JsonSerializerContext { }
Voor een afzonderlijk type:
[JsonSerializable(typeof(WeatherForecast), GenerationMode = JsonSourceGenerationMode.Serialization)] internal partial class SerializeOnlyWeatherForecastOnlyContext : JsonSerializerContext { }
Voorbeeld van het volledige programma
using System.Text.Json; using System.Text.Json.Serialization; namespace SerializeOnlyNoOptions { public class WeatherForecast { public DateTime Date { get; set; } public int TemperatureCelsius { get; set; } public string? Summary { get; set; } } [JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Serialization)] [JsonSerializable(typeof(WeatherForecast))] internal partial class SerializeOnlyContext : JsonSerializerContext { } [JsonSerializable(typeof(WeatherForecast), GenerationMode = JsonSourceGenerationMode.Serialization)] internal partial class SerializeOnlyWeatherForecastOnlyContext : JsonSerializerContext { } public class Program { public static void Main() { string jsonString; WeatherForecast weatherForecast = new() { Date = DateTime.Parse("2019-08-01"), TemperatureCelsius = 25, Summary = "Hot" }; // Use context that selects Serialization mode only for WeatherForecast. jsonString = JsonSerializer.Serialize(weatherForecast, SerializeOnlyWeatherForecastOnlyContext.Default.WeatherForecast); Console.WriteLine(jsonString); // output: //{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"} // Use a context that selects Serialization mode. jsonString = JsonSerializer.Serialize(weatherForecast, SerializeOnlyContext.Default.WeatherForecast); Console.WriteLine(jsonString); // output: //{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"} } } }
Voorbeeld van op metagegevens gebaseerde modus
Voor een volledige context:
[JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Metadata)] [JsonSerializable(typeof(WeatherForecast))] internal partial class MetadataOnlyContext : JsonSerializerContext { }
jsonString = JsonSerializer.Serialize( weatherForecast!, MetadataOnlyContext.Default.WeatherForecast);
weatherForecast = JsonSerializer.Deserialize<WeatherForecast>( jsonString, MetadataOnlyContext.Default.WeatherForecast);
Voor een afzonderlijk type:
[JsonSerializable(typeof(WeatherForecast), GenerationMode = JsonSourceGenerationMode.Metadata)] internal partial class MetadataOnlyWeatherForecastOnlyContext : JsonSerializerContext { }
jsonString = JsonSerializer.Serialize( weatherForecast!, MetadataOnlyWeatherForecastOnlyContext.Default.WeatherForecast);
weatherForecast = JsonSerializer.Deserialize<WeatherForecast>( jsonString, MetadataOnlyWeatherForecastOnlyContext.Default.WeatherForecast);
Voorbeeld van het volledige programma
using System.Text.Json; using System.Text.Json.Serialization; namespace MetadataOnlyNoOptions { public class WeatherForecast { public DateTime Date { get; set; } public int TemperatureCelsius { get; set; } public string? Summary { get; set; } } [JsonSerializable(typeof(WeatherForecast), GenerationMode = JsonSourceGenerationMode.Metadata)] internal partial class MetadataOnlyWeatherForecastOnlyContext : JsonSerializerContext { } [JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Metadata)] [JsonSerializable(typeof(WeatherForecast))] internal partial class MetadataOnlyContext : JsonSerializerContext { } public class Program { public static void Main() { string jsonString = """ { "Date": "2019-08-01T00:00:00", "TemperatureCelsius": 25, "Summary": "Hot" } """; WeatherForecast? weatherForecast; // Deserialize with context that selects metadata mode only for WeatherForecast only. weatherForecast = JsonSerializer.Deserialize<WeatherForecast>( jsonString, MetadataOnlyWeatherForecastOnlyContext.Default.WeatherForecast); Console.WriteLine($"Date={weatherForecast?.Date}"); // output: //Date=8/1/2019 12:00:00 AM // Serialize with context that selects metadata mode only for WeatherForecast only. jsonString = JsonSerializer.Serialize( weatherForecast!, MetadataOnlyWeatherForecastOnlyContext.Default.WeatherForecast); Console.WriteLine(jsonString); // output: //{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"} // Deserialize with context that selects metadata mode only. weatherForecast = JsonSerializer.Deserialize<WeatherForecast>( jsonString, MetadataOnlyContext.Default.WeatherForecast); Console.WriteLine($"Date={weatherForecast?.Date}"); // output: //Date=8/1/2019 12:00:00 AM // Serialize with context that selects metadata mode only. jsonString = JsonSerializer.Serialize( weatherForecast!, MetadataOnlyContext.Default.WeatherForecast); Console.WriteLine(jsonString); // output: //{"Date":"2019-08-01T00:00:00","TemperatureCelsius":25,"Summary":"Hot"} } } }
Ondersteuning voor brongeneratie in ASP.NET Core
Gebruik in Blazor-apps overbelastingen van en HttpClientJsonExtensions.PostAsJsonAsync uitbreidingsmethoden die een context voor het genereren van HttpClientJsonExtensions.GetFromJsonAsync bronnen gebruiken of TypeInfo<TValue>
.
Vanaf .NET 8 kunt u ook overbelastingen van extensiemethoden gebruiken die een context voor het genereren van HttpClientJsonExtensions.GetFromJsonAsAsyncEnumerable bronnen accepteren of TypeInfo<TValue>
.
Gebruik in Razor Pages-, MVC-, SignalR- en Web-API-apps de JsonSerializerOptions.TypeInfoResolver eigenschap om de context op te geven.
[JsonSerializable(typeof(WeatherForecast[]))]
internal partial class MyJsonContext : JsonSerializerContext { }
var serializerOptions = new JsonSerializerOptions
{
TypeInfoResolver = MyJsonContext.Default
};
services.AddControllers().AddJsonOptions(
static options =>
options.JsonSerializerOptions.TypeInfoResolverChain.Add(MyJsonContext.Default));
Gebruik in Razor Pages-, MVC-, SignalR- en Web-API-apps de JsonSerializerOptions.TypeInfoResolver eigenschap om de context op te geven.
[JsonSerializable(typeof(WeatherForecast[]))]
internal partial class MyJsonContext : JsonSerializerContext { }
var serializerOptions = new JsonSerializerOptions
{
TypeInfoResolver = MyJsonContext.Default
};
services.AddControllers().AddJsonOptions(
static options =>
options.JsonSerializerOptions = serializerOptions);
Gebruik in Razor Pages-, MVC-, SignalR- en Web-API-apps de AddContext methode van JsonSerializerOptions, zoals wordt weergegeven in het volgende voorbeeld:
[JsonSerializable(typeof(WeatherForecast[]))]
internal partial class MyJsonContext : JsonSerializerContext { }
services.AddControllers().AddJsonOptions(options =>
options.JsonSerializerOptions.AddContext<MyJsonContext>());
Notitie
JsonSourceGenerationMode.Serializationserialisatie van snelpaden wordt niet ondersteund voor asynchrone serialisatie.
In .NET 7 en eerdere versies is deze beperking ook van toepassing op synchrone overbelastingen van JsonSerializer.Serialize die accepteren een Stream. Vanaf .NET 8, hoewel streamingserialisatie modellen op basis van metagegevens vereist, valt het terug op snel pad als de nettoladingen klein genoeg zijn om in de vooraf vastgestelde buffergrootte te passen. Zie https://devblogs.microsoft.com/dotnet/performance-improvements-in-net-8/#json voor meer informatie.
Standaardinstellingen voor weerspiegeling uitschakelen
Omdat System.Text.Json weerspiegeling standaard wordt gebruikt, kan het aanroepen van een eenvoudige serialisatiemethode systeemeigen AOT-apps verbreken, die niet alle vereiste reflectie-API's ondersteunen. Deze onderbrekingen kunnen lastig zijn om te diagnosticeren, omdat ze onvoorspelbaar kunnen zijn, en apps worden vaak opgespoord met behulp van de CoreCLR-runtime, waar weerspiegeling werkt. Als u in plaats daarvan serialisatie op basis van weerspiegeling expliciet uitschakelt, kunt u eenvoudiger een diagnose stellen. Code die gebruikmaakt van serialisatie op basis van weerspiegeling, zorgt ervoor dat een InvalidOperationException beschrijvend bericht tijdens runtime wordt gegenereerd.
Als u standaardspiegeling in uw app wilt uitschakelen, stelt u de JsonSerializerIsReflectionEnabledByDefault
eigenschap false
MSBuild in op in uw projectbestand:
<PropertyGroup>
<JsonSerializerIsReflectionEnabledByDefault>false</JsonSerializerIsReflectionEnabledByDefault>
</PropertyGroup>
- Het gedrag van deze eigenschap is consistent, ongeacht runtime, CoreCLR of Native AOT.
- Als u deze eigenschap niet opgeeft en PublishTrimmed is ingeschakeld, wordt serialisatie op basis van reflectie automatisch uitgeschakeld.
U kunt programmatisch controleren of weerspiegeling is uitgeschakeld met behulp van de JsonSerializer.IsReflectionEnabledByDefault eigenschap. In het volgende codefragment ziet u hoe u uw serializer kunt configureren, afhankelijk van of weerspiegeling is ingeschakeld:
static JsonSerializerOptions CreateDefaultOptions()
{
return new()
{
TypeInfoResolver = JsonSerializer.IsReflectionEnabledByDefault
? new DefaultJsonTypeInfoResolver()
: MyContext.Default
};
}
Omdat de eigenschap wordt behandeld als een koppelingstijdconstante, roott de vorige methode de op weerspiegeling gebaseerde resolver niet in toepassingen die worden uitgevoerd in Systeemeigen AOT.
Opties opgeven
In .NET 8 en latere versies kunnen de meeste opties die u kunt instellen, ook worden ingesteld JsonSerializerOptions met behulp van het JsonSourceGenerationOptionsAttribute kenmerk. Het voordeel van het instellen van opties via het kenmerk is dat de configuratie tijdens het compileren wordt opgegeven, waardoor de gegenereerde MyContext.Default
eigenschap vooraf wordt geconfigureerd met alle relevante optieset.
De volgende code laat zien hoe u opties instelt met behulp van het JsonSourceGenerationOptionsAttribute kenmerk.
[JsonSourceGenerationOptions(
WriteIndented = true,
PropertyNamingPolicy = JsonKnownNamingPolicy.CamelCase,
GenerationMode = JsonSourceGenerationMode.Serialization)]
[JsonSerializable(typeof(WeatherForecast))]
internal partial class SerializationModeOptionsContext : JsonSerializerContext
{
}
Wanneer u JsonSourceGenerationOptionsAttribute
serialisatieopties opgeeft, roept u een van de volgende serialisatiemethoden aan:
Een
JsonSerializer.Serialize
methode die eenTypeInfo<TValue>
. Geef deze door aan deDefault.<TypeName>
eigenschap van uw contextklasse:jsonString = JsonSerializer.Serialize( weatherForecast, SerializationModeOptionsContext.Default.WeatherForecast);
Een
JsonSerializer.Serialize
methode die een context gebruikt. Geef deze door aan deDefault
statische eigenschap van uw contextklasse.jsonString = JsonSerializer.Serialize( weatherForecast, typeof(WeatherForecast), SerializationModeOptionsContext.Default);
Als u een methode aanroept waarmee u uw eigen exemplaar kunt Utf8JsonWriter
doorgeven, wordt de instelling van Indented de schrijver gehonoreerd in plaats van de JsonSourceGenerationOptionsAttribute.WriteIndented
optie.
Als u een contextexemplaren maakt en gebruikt door de constructor aan te roepen die een JsonSerializerOptions
exemplaar gebruikt, wordt het opgegeven exemplaar gebruikt in plaats van de opties die zijn opgegeven door JsonSourceGenerationOptionsAttribute
.
Hier volgen de voorgaande voorbeelden in een volledig programma:
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SerializeOnlyWithOptions
{
public class WeatherForecast
{
public DateTime Date { get; set; }
public int TemperatureCelsius { get; set; }
public string? Summary { get; set; }
}
[JsonSourceGenerationOptions(
WriteIndented = true,
PropertyNamingPolicy = JsonKnownNamingPolicy.CamelCase,
GenerationMode = JsonSourceGenerationMode.Serialization)]
[JsonSerializable(typeof(WeatherForecast))]
internal partial class SerializationModeOptionsContext : JsonSerializerContext
{
}
public class Program
{
public static void Main()
{
string jsonString;
WeatherForecast weatherForecast = new()
{ Date = DateTime.Parse("2019-08-01"), TemperatureCelsius = 25, Summary = "Hot" };
// Serialize using TypeInfo<TValue> provided by the context
// and options specified by [JsonSourceGenerationOptions].
jsonString = JsonSerializer.Serialize(
weatherForecast, SerializationModeOptionsContext.Default.WeatherForecast);
Console.WriteLine(jsonString);
// output:
//{
// "date": "2019-08-01T00:00:00",
// "temperatureCelsius": 0,
// "summary": "Hot"
//}
// Serialize using Default context
// and options specified by [JsonSourceGenerationOptions].
jsonString = JsonSerializer.Serialize(
weatherForecast, typeof(WeatherForecast), SerializationModeOptionsContext.Default);
Console.WriteLine(jsonString);
// output:
//{
// "date": "2019-08-01T00:00:00",
// "temperatureCelsius": 0,
// "summary": "Hot"
//}
}
}
}
Opties opgeven met behulp van JsonSerializerOptions
Sommige opties kunnen niet worden ingesteld met behulp van JsonSerializerOptions JsonSourceGenerationOptionsAttribute. Opties opgeven met behulp van JsonSerializerOptions:
- Maak een instantie van
JsonSerializerOptions
. - Maak een exemplaar van uw klasse dat is afgeleid van JsonSerializerContexten geef het
JsonSerializerOptions
exemplaar door aan de constructor. - Serialisatie- of deserialisatiemethoden aanroepen van
JsonSerializer
die een contextexemplaren ofTypeInfo<TValue>
.
Hier volgt een voorbeeldcontextklasse, gevolgd door serialisatie- en deserialisatievoorbeeldcode:
[JsonSerializable(typeof(WeatherForecast))]
internal partial class OptionsExampleContext : JsonSerializerContext
{
}
jsonString = JsonSerializer.Serialize(
weatherForecast,
typeof(WeatherForecast),
new OptionsExampleContext(
new JsonSerializerOptions(JsonSerializerDefaults.Web)));
weatherForecast = JsonSerializer.Deserialize(
jsonString,
typeof(WeatherForecast),
new OptionsExampleContext(
new JsonSerializerOptions(JsonSerializerDefaults.Web)))
as WeatherForecast;
Hier volgen de voorgaande voorbeelden in een volledig programma:
using System.Text.Json;
using System.Text.Json.Serialization;
namespace JsonSerializerOptionsExample
{
public class WeatherForecast
{
public DateTime Date { get; set; }
public int TemperatureCelsius { get; set; }
public string? Summary { get; set; }
}
[JsonSerializable(typeof(WeatherForecast))]
internal partial class OptionsExampleContext : JsonSerializerContext
{
}
public class Program
{
public static void Main()
{
string jsonString = """
{
"date": "2019-08-01T00:00:00",
"temperatureCelsius": 25,
"summary": "Hot"
}
""";
WeatherForecast? weatherForecast;
weatherForecast = JsonSerializer.Deserialize(
jsonString,
typeof(WeatherForecast),
new OptionsExampleContext(
new JsonSerializerOptions(JsonSerializerDefaults.Web)))
as WeatherForecast;
Console.WriteLine($"Date={weatherForecast?.Date}");
// output:
//Date=8/1/2019 12:00:00 AM
jsonString = JsonSerializer.Serialize(
weatherForecast,
typeof(WeatherForecast),
new OptionsExampleContext(
new JsonSerializerOptions(JsonSerializerDefaults.Web)));
Console.WriteLine(jsonString);
// output:
//{ "date":"2019-08-01T00:00:00","temperatureCelsius":25,"summary":"Hot"}
}
}
}
Brongeneratoren combineren
U kunt contracten combineren vanuit meerdere door de bron gegenereerde contexten binnen één JsonSerializerOptions exemplaar. Gebruik de JsonSerializerOptions.TypeInfoResolver eigenschap om meerdere contexten te koppelen die zijn gecombineerd met behulp van de JsonTypeInfoResolver.Combine(IJsonTypeInfoResolver[]) methode.
var options = new JsonSerializerOptions
{
TypeInfoResolver = JsonTypeInfoResolver.Combine(ContextA.Default, ContextB.Default, ContextC.Default);
};
Als u vanaf .NET 8 later een andere context wilt voorbereiden of toevoegen, kunt u dit doen met behulp van de JsonSerializerOptions.TypeInfoResolverChain eigenschap. De volgorde van de keten is belangrijk: JsonSerializerOptions voert query's uit op elk van de resolvers in hun opgegeven volgorde en retourneert het eerste resultaat dat niet null is.
options.TypeInfoResolverChain.Add(ContextD.Default); // Append to the end of the list.
options.TypeInfoResolverChain.Insert(0, ContextE.Default); // Insert at the beginning of the list.
Wijzigingen die in de TypeInfoResolverChain eigenschap zijn aangebracht, worden doorgevoerd door TypeInfoResolver en omgekeerd.
Opsommingsvelden als tekenreeksen serialiseren
Opsommingen worden standaard geserialiseerd als getallen. Als u de velden van een specifieke opsomming wilt serialiseren als tekenreeksen bij het genereren van de bron, maakt u er aantekeningen bij met het JsonStringEnumConverter<TEnum> conversieprogramma. Of als u een dekenbeleid voor alle opsommingen wilt instellen, gebruikt u het JsonSourceGenerationOptionsAttribute kenmerk.
JsonStringEnumConverter<T>
conversieprogramma
Als u opsommingsnamen wilt serialiseren als tekenreeksen met behulp van brongeneratie, gebruikt u het JsonStringEnumConverter<TEnum> conversieprogramma. (Het niet-algemene JsonStringEnumConverter type wordt niet ondersteund door de systeemeigen AOT-runtime.)
Aantekeningen toevoegen aan het opsommingstype met het JsonStringEnumConverter<TEnum> conversieprogramma met behulp van het JsonConverterAttribute kenmerk:
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
}
Maak een JsonSerializerContext klasse en annotaeer deze met het JsonSerializableAttribute kenmerk:
[JsonSerializable(typeof(WeatherForecastWithPrecipEnum))]
public partial class Context1 : JsonSerializerContext { }
Met de volgende code worden de enumnamen geserialiseerd in plaats van de numerieke waarden:
var weatherForecast = new WeatherForecastWithPrecipEnum
{
Date = DateTime.Parse("2019-08-01"),
TemperatureCelsius = 25,
Precipitation = Precipitation.Sleet
};
var options = new JsonSerializerOptions
{
WriteIndented = true,
TypeInfoResolver = Context1.Default,
};
string? jsonString = JsonSerializer.Serialize(weatherForecast, options);
De resulterende JSON ziet eruit als in het volgende voorbeeld:
{
"Date": "2019-08-01T00:00:00-07:00",
"TemperatureCelsius": 25,
"Precipitation": "Sleet"
}
Dekenbeleid
In plaats van het JsonStringEnumConverter<TEnum> type te gebruiken, kunt u een dekenbeleid toepassen om opsommingen als tekenreeksen te serialiseren met behulp van de JsonSourceGenerationOptionsAttribute. Maak een JsonSerializerContext klasse en annotaat met de JsonSerializableAttribute en JsonSourceGenerationOptionsAttribute kenmerken:
[JsonSourceGenerationOptions(UseStringEnumConverter = true)]
[JsonSerializable(typeof(WeatherForecast2WithPrecipEnum))]
public partial class Context2 : JsonSerializerContext { }
U ziet dat de opsomming het volgende niet heeft JsonConverterAttribute:
public class WeatherForecast2WithPrecipEnum
{
public DateTimeOffset Date { get; set; }
public int TemperatureCelsius { get; set; }
public Precipitation2? Precipitation { get; set; }
}
public enum Precipitation2
{
Drizzle, Rain, Sleet, Hail, Snow
}