/// <summary> /// Creates an XML document from a row tree and writes it to a stream using UTF-8 encoding. /// </summary> // If we need to start generating XML on the fly for HTTP responses, it may make sense to create an overload of this method that takes an HttpResponse // object instead of a stream. This new overload would use the HttpResponse.Output property to obtain a TextWriter and then create the XmlWriter on top of // that instead of a stream. The advantage of this approach is that the encoding of the XML would then be determined by ASP.NET, which takes into account // any request headers the client may have sent that pertain to the desired encoding of the response. public static void CreateXmlDocument(MergeRowTree rowTree, MergeFieldNameTree fieldNameTree, Stream destinationStream) { using (var writer = XmlWriter.Create(destinationStream)) { writer.WriteStartDocument(); writeRowTreeXmlElement(rowTree, fieldNameTree, writer); writer.WriteEndDocument(); } }
private static void writeRowTreeXmlElement(MergeRowTree rowTree, MergeFieldNameTree fieldNameTree, XmlWriter writer) { writer.WriteStartElement(rowTree.NodeName); foreach (var row in rowTree.Rows) { writer.WriteStartElement(rowTree.XmlRowElementName); foreach (var fieldName in fieldNameTree.FieldNames) { var mergeValue = row.Values.SingleOrDefault(i => i.Name == fieldName); if (mergeValue == null) { // Use ApplicationException instead of MailMergingException because the field names can easily be validated before this method is called. throw new ApplicationException("Merge field " + fieldName + " is invalid."); } writer.WriteStartElement(mergeValue.Name); if (mergeValue is MergeValue <string> ) { writer.WriteValue((mergeValue as MergeValue <string>).Evaluate(false)); } else { // Use ApplicationException instead of MailMergingException because the field names can easily be validated before this method is called. throw new ApplicationException("Merge field " + mergeValue.Name + " evaluates to an unsupported type."); } writer.WriteEndElement(); } foreach (var childNameAndFieldNameTree in fieldNameTree.ChildNamesAndChildren) { var childRowTree = row.Children.SingleOrDefault(i => i.NodeName == childNameAndFieldNameTree.Item1); if (childRowTree == null) { // Use ApplicationException instead of MailMergingException because the child names can easily be validated before this method is called. throw new ApplicationException("Child " + childNameAndFieldNameTree.Item1 + " is invalid."); } writeRowTreeXmlElement(childRowTree, childNameAndFieldNameTree.Item2, writer); } writer.WriteEndElement(); } writer.WriteEndElement(); }
private static void writeRowTreeXmlElement( MergeRowTree rowTree, MergeFieldNameTree fieldNameTree, XmlWriter writer ) { writer.WriteStartElement( rowTree.NodeName ); foreach( var row in rowTree.Rows ) { writer.WriteStartElement( rowTree.XmlRowElementName ); foreach( var fieldName in fieldNameTree.FieldNames ) { var mergeValue = row.Values.SingleOrDefault( i => i.Name == fieldName ); if( mergeValue == null ) { // Use ApplicationException instead of MailMergingException because the field names can easily be validated before this method is called. throw new ApplicationException( "Merge field " + fieldName + " is invalid." ); } writer.WriteStartElement( mergeValue.Name ); if( mergeValue is MergeValue<string> ) writer.WriteValue( ( mergeValue as MergeValue<string> ).Evaluate( false ) ); else { // Use ApplicationException instead of MailMergingException because the field names can easily be validated before this method is called. throw new ApplicationException( "Merge field " + mergeValue.Name + " evaluates to an unsupported type." ); } writer.WriteEndElement(); } foreach( var childNameAndFieldNameTree in fieldNameTree.ChildNamesAndChildren ) { var childRowTree = row.Children.SingleOrDefault( i => i.NodeName == childNameAndFieldNameTree.Item1 ); if( childRowTree == null ) { // Use ApplicationException instead of MailMergingException because the child names can easily be validated before this method is called. throw new ApplicationException( "Child " + childNameAndFieldNameTree.Item1 + " is invalid." ); } writeRowTreeXmlElement( childRowTree, childNameAndFieldNameTree.Item2, writer ); } writer.WriteEndElement(); } writer.WriteEndElement(); }
/// <summary> /// Creates an XML document from a row tree and writes it to a stream using UTF-8 encoding. /// </summary> // If we need to start generating XML on the fly for HTTP responses, it may make sense to create an overload of this method that takes an HttpResponse // object instead of a stream. This new overload would use the HttpResponse.Output property to obtain a TextWriter and then create the XmlWriter on top of // that instead of a stream. The advantage of this approach is that the encoding of the XML would then be determined by ASP.NET, which takes into account // any request headers the client may have sent that pertain to the desired encoding of the response. public static void CreateXmlDocument( MergeRowTree rowTree, MergeFieldNameTree fieldNameTree, Stream destinationStream ) { using( var writer = XmlWriter.Create( destinationStream ) ) { writer.WriteStartDocument(); writeRowTreeXmlElement( rowTree, fieldNameTree, writer ); writer.WriteEndDocument(); } }