Comparing Text and Binary Serialization in WCF

A question I recently ran into asked about comparing message sizes when using the default Text Message Encoder used by most bindings in WCF with the Binary Message Encoder used by the TcpBinding, without going through the entire WCF stack and having to use a protocol analyzer.

Here’s a sample application that just serializes an object using the DataContractSerializer and then runs it through both message encoders and presents the results:


using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Channels;
using System.Text;

namespace BinSerializationTest {
   [DataContract]
   class SampleDataContract {
      [DataMember]
      public string Member1;
      [DataMember]
      public int Member2;
      [DataMember]
      public string Member3;
   }

   class Program {
      static void Main(string[] args) {
         try {
            SampleDataContract dc = new SampleDataContract {
               Member1 = "Sample string 1",
               Member2 = 142234,
               Member3 = "Different data here"
            };
            byte[] xml = SerializeToXml(dc);
            Console.WriteLine("DC serialized to XML resulted in {0} bytes", xml.Length);
            byte[] bin = SerializeToBin(dc);
            Console.WriteLine("DC serialized to binary resulted in {0} bytes", bin.Length);
         } catch ( Exception ex ) {
            Console.WriteLine(ex);
         }
      }

      static byte[] SerializeToXml<T>(T obj) {
         Message msg = ObjectToMessage(obj);
         MessageEncodingBindingElement mebe = new TextMessageEncodingBindingElement();
         mebe.MessageVersion = MessageVersion.Soap12;
         return Serialize(msg, mebe.CreateMessageEncoderFactory());
      }
      static byte[] SerializeToBin<T>(T obj) {
         Message msg = ObjectToMessage(obj);
         MessageEncodingBindingElement mebe = new BinaryMessageEncodingBindingElement();
         mebe.MessageVersion = MessageVersion.Soap12;
         return Serialize(msg, mebe.CreateMessageEncoderFactory());
      }
      static byte[] Serialize(Message msg, MessageEncoderFactory factory) {
         MessageEncoder enc = factory.Encoder;
         MemoryStream stream = new MemoryStream();
         enc.WriteMessage(msg, stream);
         return stream.ToArray();
      }
      static Message ObjectToMessage<T>(T obj) {
         DataContractSerializer ser = new DataContractSerializer(typeof(T));
         return Message.CreateMessage(MessageVersion.Soap12, "", obj, ser);
      }
   }
}

Hope it’s useful!

2 Comments

  1. Pingback: Winterdom » Blog Archive » Comparing Text and Binary Serialization … | XML Developer

  2. Pingback: New and Notable 338 : Sam Gentile's Blog (if (DeveloperTask == Communication && OS == Windows)

  3. Pingback: DotNetShoutout

  4. Drew Noakes

    Thanks for this post. I distilled the methods above into one:

    private static byte[] Serialise(object obj, MessageEncodingBindingElement encoding)
    {
    encoding.MessageVersion = MessageVersion.Soap12;
    var stream = new MemoryStream();
    Message message = Message.CreateMessage(MessageVersion.Soap12, “”, obj, new DataContractSerializer(obj.GetType()));
    encoding.CreateMessageEncoderFactory().Encoder.WriteMessage(message, stream);
    return stream.ToArray();
    }

    …where ‘encoding’ is either TextMessageEncodingBindingElement or BinaryMessageEncodingBindingElement.

  5. kage

    i’m probably not the first guy to wonder what the output of this program was:

    DC serialized to XML resulted in 466 bytes
    DC serialized to binary resulted in 220 bytes

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>