RoKi0815
RoKi0815

Reputation: 58

XML Deserialize special characters

I want to deserialize an xml-file which has an special character in one of its fields. The character is hex 0x05 and results in the xml-file to . I am able to serialize the object but its not possible to deserialize it again. I am using this technique really often but this is the first time it doesnt work. This is an minimal example of the problem:

using System.Xml.Serialization;
using System.IO;

namespace XMLTest
{
    class Program
    {
        static void Main(string[] args)
        {
            SpecialCharacter testobject = new SpecialCharacter();
            string filename = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location) + @"\testfile.xml";

            //serialize
            StreamWriter writer = System.IO.File.CreateText(filename);
            XmlSerializer xmlserialize = new XmlSerializer(typeof(SpecialCharacter));
            xmlserialize.Serialize(writer, testobject);
            writer.Flush();
            writer.Close();

            //deserialize
            StreamReader reader = File.OpenText(filename);
            XmlSerializer xmldeserialize = new XmlSerializer(typeof(SpecialCharacter));
            testobject = (SpecialCharacter)xmldeserialize.Deserialize(reader);
            reader.Close();
        }
    }

    public class SpecialCharacter
    {
        public string special = char.ConvertFromUtf32(0x05).ToString();
    }
}

Upvotes: 1

Views: 2530

Answers (2)

haindl
haindl

Reputation: 3231

You have to use a special reader that has its Normalization property set to false.

So instead of

StreamReader reader = File.OpenText(filename);

use

XmlTextReader reader = new XmlTextReader(filename);

Now it should work.

Upvotes: 2

decPL
decPL

Reputation: 5402

There are two simple(-ish) solutions here:

  • Use an XmlTextReader.Create instead of File.CreateText and add new XmlReaderSettings() { CheckCharacters = false } as the second parameter. You should probably avoid doing that to be honest though, unless you're just working on files you've created yourself and know their contents.
  • Serialize your String in Base64:

public class SpecialCharacter
{
    [XmlElement(ElementName = "special")]
    public String Base64
    {
        get
        {
            return Convert.ToBase64String(System.Text.Encoding.UTF32.GetBytes(special));
        }
        set
        {
            if (value == null)
            {
                special = null;
                return;
            }

            special = System.Text.Encoding.UTF32.GetString(Convert.FromBase64String(value));
        }
    }

    [XmlIgnore]
    public String special = Char.ConvertFromUtf32(0x05).ToString();
}

Upvotes: 1

Related Questions