El constructor de copia JsonSerializerOptions incluye JsonSerializerContext

Con el lanzamiento de generación de origen en .NET 6, el constructor de copia JsonSerializerOptions se hizo de forma intencionada para omitir su estado JsonSerializerContext. Esto tenía sentido en ese momento, ya que JsonSerializerContext se diseñó para tener una relación 1:1 con instancias JsonSerializerOptions. En .NET 7, IJsonTypeInfoResolver reemplaza JsonSerializerContext para generalizar el contexto, que elimina la necesidad de acoplamiento estrecho entre JsonSerializerOptions y JsonSerializerContext. El constructor de copia ahora incluye la información IJsonTypeInfoResolver/JsonSerializerContext, que podría manifestarse como un cambio importante para algunos escenarios.

Comportamiento anterior

En .NET 6, el código siguiente se serializa correctamente. La configuración MyContext (que no admite Poco2) se descarta por el constructor de copia, y la serialización se realiza correctamente porque la nueva instancia de opciones usa por defecto la serialización basada en reflexión.

var options = new JsonSerializerOptions(MyContext.Default.Options);
JsonSerializer.Serialize(new Poco2(), options);

[JsonSerializable(typeof(Poco1))]
public partial class MyContext : JsonSerializerContext {}

public class Poco1 {}
public class Poco2 {}

Comportamiento nuevo

A partir de .NET 7, el mismo código que se muestra en la sección Comportamiento anterior produce una InvalidOperationException. Esto se debe a que el constructor de copia ahora incorpora metadatos MyContext, que no admiten contratos Poco2.

Versión introducida

.NET 7

Tipo de cambio importante

Este cambio puede afectar a la compatibilidad binaria.

Motivo del cambio

JsonSerializerContext era la única configuración ignorada por el constructor de copia. Este comportamiento fue sorprendente para algunos usuarios.

Si depende del comportamiento de .NET 6, puede anular manualmente la propiedad TypeInfoResolver para recuperar la resolución de contrato basada en reflexión:

var options = new JsonSerializerOptions(MyContext.Default.Options);
options.TypeInfoResolver = null; // Unset `MyContext.Default` as the resolver for the options instance.

API afectadas