XmlReader ottiene l'elemento predefinito dallo schema
Domanda
Questa è probabilmente una domanda ingenua su XmlReader
, ma non ho trovato una risposta nei documenti MSDN.
Supponi di avere XSD SchemaTest.xsd
<?xml version="1.0" encoding="utf-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="pageSettings">
<xs:complexType>
<xs:sequence>
<xs:element name="width" type="xs:decimal" default="8.5" minOccurs="0"/>
<xs:element name="height" type="xs:decimal" default="11" minOccurs="0"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
documento XML
ben formato SchemaTest.xml
conforme a questo schema
<?xml version="1.0" encoding="utf-8" ?>
<pageSettings xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="SchemaTest.xsd">
<width/>
<height>11</height>
</pageSettings>
e che provo a leggere questo documento con un System.FormatException
come segue.
static void Main(string[] args) {
decimal width;
decimal height;
XmlReaderSettings settings = new XmlReaderSettings();
settings.IgnoreWhitespace = true;
settings.Schemas.Add(null, "C:\\Projects\\SchemaTest\\SchemaTest\\SchemaTest.xsd");
using (XmlReader reader = XmlReader.Create("C:\\Projects\\SchemaTest\\SchemaTest\\SchemaTest.xml", settings)) {
reader.ReadStartElement();
if (reader.Name == "width") {
width = reader.ReadElementContentAsDecimal("width", "");
// if fail, width = default from schema
}
if (reader.Name == "height") {
height = reader.ReadElementContentAsDecimal("height", "");
// if fail, height = default from schema
}
reader.ReadEndElement();
}
}
Attualmente sto ricevendo un width
che indica che il contenuto sull'elemento reader
non è nel formato corretto. Sembra che <=> stia tentando di leggere il contenuto nell'elemento e non stia impostando il valore predefinito specificato nello schema. Qual è il modo corretto di gestirlo?
Inoltre, sono consapevole che per gli elementi, lo schema fornisce un valore predefinito solo se un elemento viene visualizzato con contenuto vuoto ma che non fornisce un valore predefinito se l'elemento è mancante. Ciò implica che non c'è modo di ottenere un valore predefinito per gli elementi opzionali mancanti?
Soluzione
Per quanto riguarda l'utilizzo di elementi vuoti, imposta settings.ValidationType = ValidationType.Schema
e dovresti ottenere il valore predefinito come desiderato.
Per quanto riguarda gli elementi mancanti, quelli sono considerati, beh, mancanti ;-) e quindi non hanno un valore predefinito. In teoria, è possibile analizzare lo schema (ad esempio utilizzando il modello a oggetti dello schema) per ottenere il valore predefinito. Ma questo sarebbe contro le specifiche.
Hai preso in considerazione l'utilizzo di attributi, come <pageSettings height="55"/>
? In quello scenario, dovresti ottenere i valori predefiniti per gli attributi mancanti.