Compartir a través de


Serialización y metadatos

Si la aplicación serializa y deserializa objetos, es posible que tenga que agregar entradas a los archivos de directivas en tiempo de ejecución (.rd.xml) para asegurarse de que los metadatos necesarios están presentes en tiempo de ejecución. Hay dos categorías de serializadores y cada una requiere un control diferente en el archivo de directivas en tiempo de ejecución:

  • Serializadores de terceros basados en reflexión. Estas requieren modificaciones en el archivo de directivas en tiempo de ejecución y se describen en la sección siguiente.

  • Serializadores no basados en reflexión presentes en la biblioteca de clases de .NET Framework. Pueden requerir modificaciones en el archivo de directivas en tiempo de ejecución y se describen en la sección serializadores de Microsoft.

Serializadores de terceros

Los serializadores de terceros, incluidos los Newtonsoft.JSON, normalmente se basan en la reflexión. Dado un objeto binario grande (BLOB) de datos serializados, los campos de los datos se asignan a un tipo concreto al buscar los campos del tipo de destino por su nombre. Como mínimo, el uso de estas bibliotecas provoca excepciones MissingMetadataException para cada objeto Type que intenta serializar o deserializar en una colección de List<Type>.

La manera más fácil de solucionar problemas causados por la falta de metadatos para estos serializadores es recopilar tipos que se usarán en la serialización en un único espacio de nombres (como App.Models) y aplicar una directiva de metadatos Serialize a él:

<Namespace Name="App.Models" Serialize="Required PublicAndInternal" />

Para obtener información sobre la sintaxis usada en el ejemplo, vea <Espacio de nombres> Element.

Serializadores de Microsoft

Aunque las clases DataContractSerializer, DataContractJsonSerializery XmlSerializer no se basan en la reflexión, requieren que se genere código basado en el objeto que se va a serializar o deserializar. Los constructores sobrecargados para cada serializador incluyen un parámetro Type que especifica el tipo que se va a serializar o deserializar. Cómo se especifica ese tipo en el código se define la acción que debe realizar, como se describe en las dos secciones siguientes.

Uso de typeof en el constructor

Si llama a un constructor de estas clases de serialización e incluye el operador typeof de C# en la llamada al método, no tiene que realizar ningún trabajo adicional. Por ejemplo, en cada una de las siguientes llamadas a un constructor de clase de serialización, la palabra clave typeof se usa como parte de la expresión pasada al constructor.

XmlSerializer xmlSer = new XmlSerializer(typeof(T));
DataContractSerializer dataSer = new DataContractSerializer(typeof(T));
DataContractJsonSerializer jsonSer = new DataContractJsonSerializer(typeof(T));

El compilador de .NET Native controlará automáticamente este código.

typeof se usa fuera del constructor

Si llama a un constructor de estas clases de serialización y usa el operador typeof de C# fuera de la expresión proporcionada al parámetro Type del constructor, como en el código siguiente, el compilador nativo de .NET no puede resolver el tipo.

Type t = typeof(DataSet);
XmlSerializer ser = new XmlSerializer(t);

En este caso, debe especificar el tipo en el archivo de directivas en tiempo de ejecución agregando una entrada como esta:

<Type Name="DataSet" Browse="Required Public" />

Del mismo modo, si llama a un constructor como XmlSerializer(Type, Type[]) y proporciona una matriz de objetos de Type adicionales para serializar, como en el código siguiente, el compilador nativo de .NET no puede resolver estos tipos.

XmlSerializer xSerializer = new XmlSerializer(typeof(Teacher),
                            new Type[] { typeof(Student),
                                         typeof(Course),
                                         typeof(Location) });

Agregue entradas como las siguientes para cada tipo al archivo de directivas en tiempo de ejecución:

<Type Name="t" Browse="Required Public" />

Para obtener información sobre la sintaxis usada en el ejemplo, vea <Type> Element.

Consulte también