Les options PropertyNamingPolicy, PropertyNameCaseInsensitive et Encoder sont respectées lors de la sérialisation et de la désérialisation de paires clé-valeur

JsonSerializer respecte désormais les options PropertyNamingPolicy et Encoder lors de la sérialisation des noms de propriétés Key et Value d’une instance de KeyValuePair<TKey,TValue>. En outre, JsonSerializer respecte les options PropertyNamingPolicy et PropertyNameCaseInsensitive lors de la désérialisation des instances de KeyValuePair<TKey,TValue>.

Description de la modification

Sérialisation

Dans les versions .NET Core 3.x et dans les versions 4.6.0-4.7.2 du package NuGet System.Text.Json, les propriétés des instances KeyValuePair<TKey,TValue> sont toujours sérialisées en tant que « Clé » et « Valeur » exactement, quelles que soient les options JsonSerializerOptions.PropertyNamingPolicy et JsonSerializerOptions.Encoder. L’exemple de code suivant montre comment les propriétés Key et Value ne sont pas en casse mixte après la sérialisation, même si la stratégie d’affectation de noms de propriété le demande.

var options = new JsonSerializerOptions { PropertyNamingPolicy = JsonNamingPolicy.CamelCase };
KeyValuePair<int, int> kvp = KeyValuePair.Create(1, 1);
Console.WriteLine(JsonSerializer.Serialize(kvp, options));
// Expected: {"key":1,"value":1}
// Actual: {"Key":1,"Value":1}

À compter de .NET 5, les options PropertyNamingPolicy et Encoder sont respectées lors de la sérialisation des instances de KeyValuePair<TKey,TValue>. L’exemple de code suivant montre comment les propriétés Key et Value sont en casse mixte après sérialisation, conformément à la stratégie d’affectation de noms de propriété spécifiée.

var options = new JsonSerializerOptions { PropertyNamingPolicy = JsonNamingPolicy.CamelCase };
KeyValuePair<int, int> kvp = KeyValuePair.Create(1, 1);
Console.WriteLine(JsonSerializer.Serialize(kvp, options));
// {"key":1,"value":1}

Désérialisation

Dans les versions .NET Core 3.x et dans les versions 4.7.x du package NuGet System.Text.Json, une exception JsonException est levée lorsque les noms des propriétés JSON ne sont pas précisément Key et Value, par exemple s’ils ne commencent pas par une lettre majuscule. L’exception est levée même si une stratégie de nommage de propriété spécifiée l’autorise expressément.

var options = new JsonSerializerOptions { PropertyNamingPolicy = JsonNamingPolicy.CamelCase };
string json = @"{""key"":1,""value"":1}";
// Throws JsonException.
JsonSerializer.Deserialize<KeyValuePair<int, int>>(json, options);

À partir de .NET 5, les options PropertyNamingPolicy et PropertyNameCaseInsensitive sont respectées lors de la désérialisation à l’aide de JsonSerializer. Par exemple, l’extrait de code suivant montre la désérialisation réussie des noms de propriétés en minuscules Key et Value, car la stratégie d’affectation de noms de propriété spécifiée l’autorise.

var options = new JsonSerializerOptions { PropertyNamingPolicy = JsonNamingPolicy.CamelCase };
string json = @"{""key"":1,""value"":1}";

KeyValuePair<int, int> kvp = JsonSerializer.Deserialize<KeyValuePair<int, int>>(json);
Console.WriteLine(kvp.Key); // 1
Console.WriteLine(kvp.Value); // 1

Pour prendre en charge les charges utiles sérialisées avec les versions précédentes, « Key » et « Value » sont à casse spéciale pour correspondre lors de la désérialisation. Même si les noms des propriétés Key et Value ne sont pas en casse mixte conformément à l’option PropertyNamingPolicy dans l’exemple de code suivant, ils sont désérialisés correctement.

var options = new JsonSerializerOptions { PropertyNamingPolicy = JsonNamingPolicy.CamelCase };
string json = @"{""Key"":1,""Value"":1}";

KeyValuePair<int, int> kvp = JsonSerializer.Deserialize<KeyValuePair<int, int>>(json);
Console.WriteLine(kvp.Key); // 1
Console.WriteLine(kvp.Value); // 1

Version introduite

5,0

Raison du changement

Des retours clients substantiels indiquent que le PropertyNamingPolicy doit être respecté. Par souci d’exhaustivité, les options PropertyNameCaseInsensitive et Encoder sont également respectées, de sorte que les instances KeyValuePair<TKey,TValue> sont traitées de la même façon que tout autre objet CLR (POCO).

Si cette modification vous perturbe, vous pouvez utiliser un convertisseur personnalisé qui implémente la sémantique souhaitée.

API affectées