.NET 6 XmlSerializer Pretty print - c#

I've this sample .NET 6 program printing out a serialised object to XML:
using System.Text;
using System.Xml.Serialization;
var serializer = new XmlSerializer(typeof(Order));
var order = new Order
{
Address = new Address
{
FirstName = "Name"
}
};
await using var memoryStream = new MemoryStream();
var streamWriter = new StreamWriter(memoryStream, Encoding.UTF8);
serializer.Serialize(streamWriter, order);
var result = Encoding.UTF8.GetString(memoryStream.ToArray());
Console.WriteLine(result);
public class Order
{
public Address Address;
}
public class Address
{
public string FirstName;
}
This results in this output:
<?xml version="1.0" encoding="utf-8"?><Order xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"><Address><FirstName>Name</FirstName></Address></Order>
In .NET 5 and .NET Core 3 similar code results in pretty printed XML like below. How can I format this XML in .NET6?
<?xml version="1.0" encoding="utf-8"?>
<Order xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Address>
<FirstName>Name</FirstName>
</Address>
</Order>

To write indented xml you can use XmlTextWriter (instead of just StreamWriter) with Formatting set to Formatting.Indented:
await using var memoryStream = new MemoryStream();
XmlTextWriter streamWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
streamWriter.Formatting = Formatting.Indented;
serializer.Serialize(streamWriter, order);
var result = Encoding.UTF8.GetString(memoryStream.ToArray());
UPD
As #sveinungf wrote in the comment - using XmlWriter.Create is recommended approach, so the code can look like this (also note that Create method can accept StringBuilder or file name which can be more convenient in some scenarios):
await using var memoryStream = new MemoryStream();
var streamWriter = XmlWriter.Create(memoryStream, new()
{
Encoding = Encoding.UTF8,
Indent = true
});
serializer.Serialize(streamWriter, order);
var result = Encoding.UTF8.GetString(memoryStream.ToArray());

Related

Obtaining the XML encoding from an XML declaration fragment: XmlDeclaration is not supported for partial content parsing

I'm working on some code to read an XML fragment which contains an XML declaration, e.g. <?xml version="1.0" encoding="utf-8"?> and parse the encoding. From MSDN, I should be able to do it like this:
var nt = new NameTable();
var mgr = new XmlNamespaceManager(nt);
var context = new XmlParserContext(null, mgr, null, XmlSpace.None);
var reader = new System.Xml.XmlTextReader(#"<?xml version=""1.0"" encoding=""UTF-8""?>",
System.Xml.XmlNodeType.XmlDeclaration, context);
However, I'm getting a System.Xml.XmlException on the call to the System.Xml.XmlTextReader constructor with an error message:
XmlNodeType XmlDeclaration is not supported for partial content
parsing.
I've googled this error in quotes -- exactly zero results found (edit: now there's one result: this post) -- and without quotes, which yields nothing useful. I've also looked at MSDN for the XmlNodeType, and it doesn't say anything about it not being supported.
What am I missing here? How can I get an XmlTextReader instance from an XML declaration fragment?
Note, my goal here is just to determine the encoding of a partially-built XML document where I'm making the assumption that it at least contains a declaration node; thus, I'm trying to get reader.Encoding. If there's another way to do that, I'm open to that.
At present, I'm parsing the declaration manually using regex, which is not the best approach.
Update: Getting the encoding from XML documentation or from XML fragment:
Here's a way to get the encoding without having to resort to fake root, using XmlReader.Create.
private static string GetXmlEncoding(string xmlString)
{
if (string.IsNullOrWhiteSpace(xmlString)) throw new ArgumentException("The provided string value is null or empty.");
using (var stringReader = new StringReader(xmlString))
{
var settings = new XmlReaderSettings { ConformanceLevel = ConformanceLevel.Fragment };
using (var xmlReader = XmlReader.Create(stringReader, settings))
{
if (!xmlReader.Read()) throw new ArgumentException(
"The provided XML string does not contain enough data to be valid XML (see https://msdn.microsoft.com/en-us/library/system.xml.xmlreader.read)");
var result = xmlReader.GetAttribute("encoding");
return result;
}
}
}
Here's the output, with a full and fragment XML:
If you want to have System.Text.Encoding, you can modify the code to look like this:
private static Encoding GetXmlEncoding(string xmlString)
{
using (StringReader stringReader = new StringReader(xmlString))
{
var settings = new XmlReaderSettings { ConformanceLevel = ConformanceLevel.Fragment };
var reader = XmlReader.Create(stringReader, settings);
reader.Read();
var encoding = reader.GetAttribute("encoding");
var result = Encoding.GetEncoding(encoding);
return result;
}
}
Old answer:
As you mentioned, XmlTextReader's Encoding-property contains the encoding.
Here's a full Console app's source code which hopefully is useful:
class Program
{
static void Main(string[] args)
{
var asciiXML = #"<?xml version=""1.0"" encoding=""ASCII""?><note><to>Tove</to><from>Jani</from><heading>Reminder</heading><body>Don't forget me this weekend!</body></note>";
var utf8XML = #"<?xml version=""1.0"" encoding=""UTF-8""?><note><to>Tove</to><from>Jani</from><heading>Reminder</heading><body>Don't forget me this weekend!</body></note>";
var asciiResult = GetXmlEncoding(asciiXML);
var utfResult = GetXmlEncoding(utf8XML);
Console.WriteLine(asciiResult);
Console.WriteLine(utfResult);
Console.ReadLine();
}
private static Encoding GetXmlEncoding(string s)
{
var stream = new MemoryStream(Encoding.UTF8.GetBytes(s));
using (var xmlreader = new XmlTextReader(stream))
{
xmlreader.MoveToContent();
var encoding = xmlreader.Encoding;
return encoding;
}
}
}
Here's the output from the program:
If you know that the XML only contains the declaration, maybe you can add an empty root? So for example:
var fragmentResult = GetXmlEncoding(xmlFragment + "<root/>");
Good evening, here's the solution with a System.Text.Encoding as output.
I made it to be clear, and step by step.
class Program
{
static void Main(string[] args)
{
var line = File.ReadLines(YourFileName).First();
var correctXml = line + "<Root></Root>";
var xml = XDocument.Parse(correctXml);
var stringEncoding = xml.Declaration.Encoding;
var encoding = System.Text.Encoding.GetEncoding(stringEncoding);
}
}
Maybe late but you can use below code after loading it in a XmlDocument
static string getEncoding(XmlDocument xml)
{
if (xml.FirstChild.NodeType == XmlNodeType.XmlDeclaration)
{
return (xml.FirstChild as XmlDeclaration).Encoding;
}
return "utf-8";
}
If you have a byte array as input, try something like this:
private Encoding getEncoding(byte[] data)
{
XmlReaderSettings settings = new XmlReaderSettings();
settings.DtdProcessing = DtdProcessing.Ignore;
XmlDocument doc = new XmlDocument();
MemoryStream ms = new MemoryStream(data);
XmlReader reader = XmlReader.Create(ms, settings);
doc.Load(reader);
XmlDeclaration declaration = doc.ChildNodes.OfType<XmlDeclaration>().FirstOrDefault();
return Encoding.GetEncoding(declaration.Encoding);
}

Using SAXON 9.5 (nuget) with Schematron

I am running this code:
string path = AppDomain.CurrentDomain.BaseDirectory;
// Uri schemaUri = new Uri(#"file:\\" + path + #"\sch\patient.sch");
Uri totransformEE = new Uri(#"file:\\" + path + #"\po\po-schema.sch");
Uri transformER = new Uri(#"file:\\" + path + #"\xsl\conformance1-5.xsl");
///////////////////////////////
// Crate Schemtron xslt to be applied
///////////////////////////////
// Create a Processor instance.
Processor processor = new Processor();
// Load the source document
XdmNode input = processor.NewDocumentBuilder().Build(totransformEE);
// Create a transformer for the stylesheet.
XsltTransformer transformer = processor.NewXsltCompiler().Compile(transformER).Load();
// Set the root node of the source document to be the initial context node
transformer.InitialContextNode = input;
// Create a serializer
Serializer serializer = new Serializer();
MemoryStream st = new MemoryStream();
serializer.SetOutputStream(st);
// Transform the source XML to System.out.
transformer.Run(serializer);
st.Position = 0;
System.IO.StreamReader rd = new System.IO.StreamReader(st);
string xsltSchematronStylesheet = rd.ReadToEnd();
System.Diagnostics.Debug.WriteLine(xsltSchematronStylesheet);
// Load the source document
Uri transformEE2 = new Uri(#"file:\\" + path + #"\po\po-bad.xml");
var documentbuilder2 = processor.NewDocumentBuilder();
XdmNode input2 = documentbuilder2.Build(transformEE2);
////// Create a transformer for the stylesheet.
StringReader sr2 = new StringReader(xsltSchematronStylesheet);
XsltTransformer transformer2 = processor.NewXsltCompiler().Compile(sr2).Load();
// Set the root node of the source document to be the initial context node
transformer2.InitialContextNode = input2;
// Create a serializer
Serializer serializer2 = new Serializer();
MemoryStream st2 = new MemoryStream();
serializer.SetOutputStream(st2);
transformer2.MessageListener = new MyMessageListener();
// Transform the source XML to System.out.
transformer2.Run(serializer2);
st2.Position = 0;
System.IO.StreamReader rd2 = new System.IO.StreamReader(st2);
string xsltSchematronResult = rd2.ReadToEnd();
System.Diagnostics.Debug.WriteLine(xsltSchematronResult);
I get what appears to be an XSLT file when examining xsltSchematronStylesheet. However the stream at the end st2 has 0 length. Also, MyMessageListener.Message receives no calls (I used a break point).
I am not sure if I have bad code, bad sample files, etc.
I believe my sample files are correct, but maybe I have bad ones or am missing some.
Does anyone know why no data is returned to the stream st2. If not can you direct me to a good simple sample that has all the files and works?
My real underlying problem was finding simple complete sample code to do Schematron in .Net. So for the next guy here is the sample I was looking for. I have tried to make this as complete as possible. If I missed something, leave a comment.
Create a unit test project
Run the Nuget Command
Download the Schematron files
Use the included classes and sch, xml files.
Run the test program
Nuget Saxon Commandline:
Install-Package Saxon-HE
Download Up to date Schematron Files
http://www.schematron.com/tmp/iso-schematron-xslt2.zip
UnitTest:
using System;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.IO;
namespace SOAPonFHIR.Test
{
[TestClass]
public class Schematron
{
[TestMethod]
public void XSLT_SAXON_Simple_Schematron2()
{
///////////////////////////////
// Transform original Schemtron
///////////////////////////////
string path = AppDomain.CurrentDomain.BaseDirectory;
Uri schematron = new Uri(#"file:\\" + path + #"\simple\input.sch");
Uri schematronxsl = new Uri(#"file:\\" + path + #"\xsl_2.0\iso_svrl_for_xslt2.xsl");
Stream schematrontransform = new Test.XSLTransform().Transform(schematron, schematronxsl);
///////////////////////////////
// Apply Schemtron xslt
///////////////////////////////
FileStream xmlstream = new FileStream(path + #"\simple\input.xml", FileMode.Open, FileAccess.Read, FileShare.Read);
Stream results = new Test.XSLTransform().Transform(xmlstream, schematrontransform);
System.Diagnostics.Debug.WriteLine("RESULTS");
results.Position = 0;
System.IO.StreamReader rd2 = new System.IO.StreamReader(results);
string xsltSchematronResult = rd2.ReadToEnd();
System.Diagnostics.Debug.WriteLine(xsltSchematronResult);
}
}
}
Transform Class:
using System;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.Xml;
using System.Xml.XPath;
using System.Xml.Xsl;
using Saxon.Api;
using System.IO;
using System.Xml.Schema;
using System.Collections.Generic;
namespace SOAPonFHIR.Test
{
public class XSLTransform
{
public Stream Transform(Uri xmluri, Uri xsluri)
{
// Create a Processor instance.
Processor processor = new Processor();
// Load the source document
XdmNode input = processor.NewDocumentBuilder().Build(xmluri);
// Create a transformer for the stylesheet.
var compiler = processor.NewXsltCompiler();
compiler.ErrorList = new System.Collections.Generic.List<Exception>();
XsltTransformer transformer = compiler.Compile(xsluri).Load();
if (compiler.ErrorList.Count != 0)
throw new Exception("Exception loading xsl!");
// Set the root node of the source document to be the initial context node
transformer.InitialContextNode = input;
// Create a serializer
Serializer serializer = new Serializer();
MemoryStream results = new MemoryStream();
serializer.SetOutputStream(results);
// Transform the source XML to System.out.
transformer.Run(serializer);
//get the string
results.Position = 0;
return results;
}
public System.IO.Stream Transform(System.IO.Stream xmlstream, System.IO.Stream xslstream)
{
// Create a Processor instance.
Processor processor = new Processor();
// Load the source document
var documentbuilder = processor.NewDocumentBuilder();
documentbuilder.BaseUri = new Uri("file://c:/" );
XdmNode input = documentbuilder.Build(xmlstream);
// Create a transformer for the stylesheet.
var compiler = processor.NewXsltCompiler();
compiler.ErrorList = new System.Collections.Generic.List<Exception>();
compiler.XmlResolver = new XmlUrlResolver();
XsltTransformer transformer = compiler.Compile(xslstream).Load();
if (compiler.ErrorList.Count != 0)
throw new Exception("Exception loading xsl!");
// Set the root node of the source document to be the initial context node
transformer.InitialContextNode = input;
// Create a serializer
Serializer serializer = new Serializer();
MemoryStream results = new MemoryStream();
serializer.SetOutputStream(results);
// Transform the source XML to System.out.
transformer.Run(serializer);
//get the string
results.Position = 0;
return results;
}
}
}
Schematron File
<?xml version="1.0" encoding="utf-8"?>
<iso:schema
xmlns="http://purl.oclc.org/dsdl/schematron"
xmlns:iso="http://purl.oclc.org/dsdl/schematron"
xmlns:dp="http://www.dpawson.co.uk/ns#"
queryBinding='xslt2'
schemaVersion='ISO19757-3'>
<iso:title>Test ISO schematron file. Introduction mode</iso:title>
<iso:ns prefix='dp' uri='http://www.dpawson.co.uk/ns#'/>
<iso:pattern>
<iso:rule context="chapter">
<iso:assert
test="title">A chapter should have a title</iso:assert>
</iso:rule>
</iso:pattern>
</iso:schema>
XML File
<?xml version="1.0" encoding="utf-8" ?>
<doc>
<chapter id="c1">
<title>chapter title</title>
<para>Chapter content</para>
</chapter>
<chapter id="c2">
<title>chapter 2 title</title>
<para>Content</para>
</chapter>
<chapter id="c3">
<title>Title</title>
<para>Chapter 3 content</para>
</chapter>
</doc>
Results:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<svrl:schematron-output xmlns:svrl="http://purl.oclc.org/dsdl/svrl"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:saxon="http://saxon.sf.net/"
xmlns:schold="http://www.ascc.net/xml/schematron"
xmlns:iso="http://purl.oclc.org/dsdl/schematron"
xmlns:xhtml="http://www.w3.org/1999/xhtml"
xmlns:dp="http://www.dpawson.co.uk/ns#"
title="Test ISO schematron file. Introduction mode"
schemaVersion="ISO19757-3"><!--  
 
 
-->
<svrl:ns-prefix-in-attribute-values uri="http://www.dpawson.co.uk/ns#" prefix="dp"/>
<svrl:active-pattern document="file:///c:/"/>
<svrl:fired-rule context="chapter"/>
<svrl:fired-rule context="chapter"/>
<svrl:fired-rule context="chapter"/>
</svrl:schematron-output>
Resolution:
serializer.SetOutputStream(st2);
should be
serializer2.SetOutputStream(st2);

Error in XML document [duplicate]

This question already has answers here:
Can't Load asset as XML file
(2 answers)
Closed 8 years ago.
i'm trying to Deserialize an Xml document to an array of object. I did it with Xna but for monogame i have to change my method.
this is how i deserialize :
public static XmlData[] DeserializeFromXml<XmlData>(string inputFile)
{
XmlSerializer s = new XmlSerializer(typeof(XmlData));
XmlData[] deserializedObject = default(XmlData[]);
byte[] byteArray = Encoding.UTF8.GetBytes(inputFile);
//byte[] byteArray = Encoding.ASCII.GetBytes(contents);
MemoryStream stream = new MemoryStream(byteArray);
using (TextReader textReader = new StreamReader(stream))
{
deserializedObject = (XmlData[])s.Deserialize(textReader);
}
return deserializedObject;
}
my class XmlData :
public class XmlData
{
public int id;
public int posx;
public int posy;
public int rot;
public int Width;
public int Height;
}
my xml file :
<?xml version="1.0" encoding="utf-8" ?>
<Asset Type="XmlData[]">
<Item>
<id>17</id>
<posx>54</posx>
<posy>30</posy>
<rot>90</rot>
<Width>184</Width>
<Height>5</Height>
</Item>
<Item>
<id>1</id>
<posx>200</posx>
<posy>120</posy>
<rot>0</rot>
<Width>100</Width>
<Height>90</Height>
</Item>
</Asset>
And i have the following error :
There is an error in XML document (1, 1). (i'm using monogame)
Encoding.UTF8.GetBytes(inputFile);
You are trying to decode the filename here not the filecontent.
Try something like
using (StreamReader reader = StreamReader(inputFile,Encoding.UTF8,true))
{
XmlSerializer serializer = new XmlSerializer(typeof(XmlData));
return (XmlData[])serializer.Deserialize(reader);
}
Ok This will work on your xml file:
public static List<XmlData> DeserializeFromXml(string inputFile)
{
List<XmlData> mydata = new List<XmlData>();
XmlSerializer s = new XmlSerializer(typeof(List<XmlData>),new XmlRootAttribute("Asset"));
//XmlData[] deserializedObject = default(XmlData[]);
//byte[] byteArray = Encoding.UTF8.GetBytes(inputFile);
//byte[] byteArray = Encoding.ASCII.GetBytes(contents);
//MemoryStream stream = new MemoryStream(byteArray);
using (TextReader txtReader = new StreamReader(inputFile))
{
mydata = (List<XmlData>)s.Deserialize(txtReader);
}
return mydata;
}
Change <Item> to <XmlData> and you are well, or, place this in your XmlData class declaration:
[XmlType("Item")]
public class XmlData
you can use this code !!
using (XmlTextReader xmlReader = new XmlTextReader(yourfile))
{
XDocument xdoc = XDocument.Load(xmlReader);
var programs= from programItem in xdoc.Root.Elements()
select new xmldata {
Id = Convert.ToInt32( programItem.Attribute("Id").Value),
posx = Convert.ToInt32( programItem.Attribute("posx").Value),
poxy = Convert.ToInt32( programItem.Attribute("poxy").Value),
};
result = programs.ToList();
}
Thanks to #terrybozzio i finally find a way to read my xml file, before i had to convert it to a stream. But With Monogame Framework not alll methods are implemented.
Way to do it :
public static List<XmlData> DeserializeFromXml(string inputFile)
{
List<XmlData> mydata = new List<XmlData>();
XmlSerializer s = new XmlSerializer(typeof(List<XmlData>), new XmlRootAttribute("Asset"));
//XmlData[] deserializedObject = default(XmlData[]);
// byte[] byteArray = Encoding.UTF8.GetBytes(inputFile);
// byte[] byteArray = Encoding.ASCII.GetBytes(inputfile);
// MemoryStream stream = new MemoryStream(byteArray);
Stream test = TitleContainer.OpenStream("pets.xml");
using (TextReader txtReader = new StreamReader(test))
{
mydata = (List<XmlData>)s.Deserialize(txtReader);
}
return mydata;
}

How do I add a default namespace with no prefix using XMLSerializer

I am trying to generate an XML document that contains the default namespace without a prefix using XmlSerializer, e.g.
<?xml version="1.0" encoding="utf-8" ?>
<MyRecord ID="9266" xmlns="http://www.website.com/MyRecord">
<List>
<SpecificItem>
Using the following code ...
string xmlizedString = null;
MemoryStream memoryStream = new MemoryStream();
XmlSerializer xs = new XmlSerializer(typeof(ExportMyRecord));
XmlSerializerNamespaces xmlnsEmpty = new XmlSerializerNamespaces();
xmlnsEmpty.Add(string.Empty, string.Empty);
XmlTextWriter xmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
xs.Serialize(xmlTextWriter, myRecord, xmlnsEmpty);
memoryStream = (MemoryStream)xmlTextWriter.BaseStream;
xmlizedString = this.UTF8ByteArrayToString(memoryStream.ToArray());
and class structure ...
[Serializable]
[XmlRoot("MyRecord")]
public class ExportMyRecord
{
[XmlAttribute("ID")]
public int ID { get; set; }
Now, I've tried various options ...
XmlSerializer xs = new XmlSerializer
(typeof(ExportMyRecord),"http://www.website.com/MyRecord");
or ...
[XmlRoot(Namespace = "http://www.website.com/MyRecord", ElementName="MyRecord")]
gives me ...
<?xml version="1.0" encoding="utf-8"?>
<q1:MylRecord ID="9266" xmlns:q1="http://www.website.com/MyRecord">
<q1:List>
<q1:SpecificItem>
I need the XML to have the namespace without the prefix as it's going to a third party provider and they reject all other alternatives.
There you go:
ExportMyRecord instance = GetInstanceToSerializeFromSomewhere();
XmlSerializerNamespaces xmlnsEmpty = new XmlSerializerNamespaces();
xmlnsEmpty.Add(string.Empty, "http://www.website.com/MyRecord");
var serializer = new XmlSerializer(
instance.GetType(),
"http://www.website.com/MyRecord"
);
Here's a generic implementation that can be used for any type:
public static void Serialize<T>(T instance, string defaultNamespace, Stream stream)
{
var namespaces = new XmlSerializerNamespaces();
namespaces.Add(string.Empty, defaultNamespace);
var serializer = new XmlSerializer(typeof(T), defaultNamespace);
serializer.Serialize(stream, instance, namespaces);
}

Easier way to serialize C# class as XML text

While trying to answer another question, I was serializing a C# object to an XML string. It was surprisingly hard; this was the shortest code snippet I could come up with:
var yourList = new List<int>() { 1, 2, 3 };
var ms = new MemoryStream();
var xtw = new XmlTextWriter(ms, Encoding.UTF8);
var xs = new XmlSerializer(yourList.GetType());
xs.Serialize(xtw, yourList);
var encoding = new UTF8Encoding();
string xmlEncodedList = encoding.GetString(ms.GetBuffer());
The result is okay:
<?xml version="1.0" encoding="utf-8"?>
<ArrayOfInt
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<int>1</int>
<int>2</int>
<int>3</int>
</ArrayOfInt>
But the snippet is more complicated than I think it should be. I can't believe you have to know about encoding and MemoryStream for this simple task.
Is there a shorter way to serialize an object to an XML string?
A little shorter :-)
var yourList = new List<int>() { 1, 2, 3 };
using (var writer = new StringWriter())
{
new XmlSerializer(yourList.GetType()).Serialize(writer, yourList);
var xmlEncodedList = writer.GetStringBuilder().ToString();
}
Although there's a flaw with this previous approach that's worth pointing out. It will generate an utf-16 header as we use StringWriter so it is not exactly equivalent to your code. To get utf-8 header we should use a MemoryStream and an XmlWriter which is an additional line of code:
var yourList = new List<int>() { 1, 2, 3 };
using (var stream = new MemoryStream())
{
using (var writer = XmlWriter.Create(stream))
{
new XmlSerializer(yourList.GetType()).Serialize(writer, yourList);
var xmlEncodedList = Encoding.UTF8.GetString(stream.ToArray());
}
}
Simply if you want to use UTF8 encoding then do it like this
public class StringWriterUtf8 : System.IO.StringWriter
{
public override Encoding Encoding
{
get
{
return Encoding.UTF8;
}
}
}
and then use StringWriterUtf8 insread of StringWriter like this
using (StringWriterUtf8 textWriter = new StringWriterUtf8())
{
serializer.Serialize(textWriter, tr, ns);
xmlText = textWriter.ToString();
}
Write an extension method or a wrapper class/function to encapsulate the snippet.
You don't need the MemoryStream, just use a StringWriter :
var yourList = new List<int>() { 1, 2, 3 };
using (StringWriter sw = new StringWriter())
{
var xs = new XmlSerializer(yourList.GetType());
xs.Serialize(sw, yourList);
string xmlEncodedList = sw.ToString();
}

Categories