OperationFormatter.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ WCF / WCF / 3.5.30729.1 / untmp / Orcas / SP / ndp / cdf / src / WCF / ServiceModel / System / ServiceModel / Dispatcher / OperationFormatter.cs / 1 / OperationFormatter.cs

                            //------------------------------------------------------------------------------ 
// Copyright (c) Microsoft Corporation.  All rights reserved.
//-----------------------------------------------------------------------------
namespace System.ServiceModel.Dispatcher
{ 
    using System.Collections;
    using System.ServiceModel; 
    using System.ServiceModel.Description; 
    using System.Collections.Generic;
    using System.Collections.ObjectModel; 
    using System.Diagnostics;
    using System.IO;
    using System.Runtime.Serialization;
    using System.Reflection; 
    using System.Xml;
    using System.ServiceModel.Diagnostics; 
    using System.ServiceModel.Channels; 

    abstract internal class OperationFormatter : IClientMessageFormatter, IDispatchMessageFormatter 
    {
        MessageDescription replyDescription;
        MessageDescription requestDescription;
        XmlDictionaryString action; 
        XmlDictionaryString replyAction;
        protected StreamFormatter requestStreamFormatter, replyStreamFormatter; 
        XmlDictionary dictionary; 
        string operationName;
        static object[] emptyObjectArray = new object[0]; 

        public OperationFormatter(OperationDescription description, bool isRpc, bool isEncoded)
        {
            Validate(description, isRpc, isEncoded); 
            this.requestDescription = description.Messages[0];
            if (description.Messages.Count == 2) 
                this.replyDescription = description.Messages[1]; 

            int stringCount = 3 + requestDescription.Body.Parts.Count; 
            if (replyDescription != null)
                stringCount += 2 + replyDescription.Body.Parts.Count;

            dictionary = new XmlDictionary(stringCount * 2); 
            GetActions(description, dictionary, out this.action, out this.replyAction);
            operationName = description.Name; 
            requestStreamFormatter = StreamFormatter.Create(requestDescription, operationName, true/*isRequest*/); 
            if (replyDescription != null)
                replyStreamFormatter = StreamFormatter.Create(replyDescription, operationName, false/*isResponse*/); 
        }

        protected abstract void AddHeadersToMessage(Message message, MessageDescription messageDescription, object[] parameters, bool isRequest);
        protected abstract void SerializeBody(XmlDictionaryWriter writer, MessageVersion version, string action, MessageDescription messageDescription, object returnValue, object[] parameters, bool isRequest); 
        protected abstract void GetHeadersFromMessage(Message message, MessageDescription messageDescription, object[] parameters, bool isRequest);
        protected abstract object DeserializeBody(XmlDictionaryReader reader, MessageVersion version, string action, MessageDescription messageDescription, object[] parameters, bool isRequest); 
 
        protected virtual void WriteBodyAttributes(XmlDictionaryWriter writer, MessageVersion messageVersion)
        { 
        }

        internal string RequestAction
        { 
            get
            { 
                if (action != null) 
                    return action.Value;
                return null; 
            }
        }
        internal string ReplyAction
        { 
            get
            { 
                if (replyAction != null) 
                    return replyAction.Value;
                return null; 
            }
        }

        protected XmlDictionary Dictionary 
        {
            get { return dictionary; } 
        } 

        protected string OperationName 
        {
            get { return this.operationName; }
        }
 
        protected MessageDescription ReplyDescription
        { 
            get { return replyDescription; } 
        }
 
        protected MessageDescription RequestDescription
        {
            get { return requestDescription; }
        } 

        protected XmlDictionaryString AddToDictionary(string s) 
        { 
            return AddToDictionary(dictionary, s);
        } 

        public object DeserializeReply(Message message, object[] parameters)
        {
            if (message == null) 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("message");
 
            if (parameters == null) 
                throw TraceUtility.ThrowHelperError(new ArgumentNullException("parameters"), message);
 
            object result = null;
            if (replyDescription.IsTypedMessage)
            {
                object typeMessageInstance = CreateTypedMessageInstance(replyDescription.MessageType); 
                TypedMessageParts typedMessageParts = new TypedMessageParts(typeMessageInstance, replyDescription);
                object[] parts = new object[typedMessageParts.Count]; 
 
                GetPropertiesFromMessage(message, replyDescription, parts);
                GetHeadersFromMessage(message, replyDescription, parts, false/*isRequest*/); 
                DeserializeBodyContents(message, parts, false/*isRequest*/);

                // copy values into the actual field/properties
                typedMessageParts.SetTypedMessageParts(parts); 

                result = typeMessageInstance; 
            } 
            else
            { 
                GetPropertiesFromMessage(message, replyDescription, parameters);
                GetHeadersFromMessage(message, replyDescription, parameters, false/*isRequest*/);
                result = DeserializeBodyContents(message, parameters, false/*isRequest*/);
            } 
            return result;
        } 
 
        private static object CreateTypedMessageInstance(Type messageContractType)
        { 
            BindingFlags bindingFlags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.CreateInstance | BindingFlags.NonPublic;
            try
            {
                object typeMessageInstance = Activator.CreateInstance( 
                    messageContractType,
                    bindingFlags, 
                    null, emptyObjectArray, null); 
                return typeMessageInstance;
            } 
            catch (MissingMethodException mme)
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.SFxMessageContractRequiresDefaultConstructor, messageContractType.FullName), mme));
            } 
        }
 
        public void DeserializeRequest(Message message, object[] parameters) 
        {
            if (message == null) 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("message");

            if (parameters == null)
                throw TraceUtility.ThrowHelperError(new ArgumentNullException("parameters"), message); 
            if (requestDescription.IsTypedMessage)
            { 
                object typeMessageInstance = CreateTypedMessageInstance(requestDescription.MessageType); 
                TypedMessageParts typedMessageParts = new TypedMessageParts(typeMessageInstance, requestDescription);
                object[] parts = new object[typedMessageParts.Count]; 

                GetPropertiesFromMessage(message, requestDescription, parts);
                GetHeadersFromMessage(message, requestDescription, parts, true/*isRequest*/);
                DeserializeBodyContents(message, parts, true/*isRequest*/); 

                // copy values into the actual field/properties 
                typedMessageParts.SetTypedMessageParts(parts); 

                parameters[0] = typeMessageInstance; 
            }
            else
            {
                GetPropertiesFromMessage(message, requestDescription, parameters); 
                GetHeadersFromMessage(message, requestDescription, parameters, true/*isRequest*/);
                DeserializeBodyContents(message, parameters, true/*isRequest*/); 
            } 
        }
 
        object DeserializeBodyContents(Message message, object[] parameters, bool isRequest)
        {
            MessageDescription messageDescription;
            StreamFormatter streamFormatter; 
            if(isRequest)
            { 
                streamFormatter = requestStreamFormatter; 
                messageDescription = requestDescription;
            } 
            else
            {
                streamFormatter = replyStreamFormatter;
                messageDescription = replyDescription; 
            }
            if (streamFormatter != null) 
            { 
                object retVal = null;
                streamFormatter.Deserialize(parameters, ref retVal, message); 
                return retVal;
            }

            if (message.IsEmpty) 
            {
                return null; 
            } 
            else
            { 
                XmlDictionaryReader reader = message.GetReaderAtBodyContents();
                using (reader)
                {
                    object body = DeserializeBody(reader, message.Version, RequestAction, messageDescription, parameters, isRequest); 
                    message.ReadFromBodyContentsToEnd(reader);
                    return body; 
                } 
            }
        } 

        public Message SerializeRequest(MessageVersion messageVersion, object[] parameters)
        {
            object[] parts = null; 

            if (messageVersion == null) 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("messageVersion"); 

            if (parameters == null) 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("parameters");
            if (requestDescription.IsTypedMessage)
            {
                TypedMessageParts typedMessageParts = new TypedMessageParts(parameters[0], requestDescription); 

                // copy values from the actual field/properties 
                parts = new object[typedMessageParts.Count]; 
                typedMessageParts.GetTypedMessageParts(parts);
            } 
            else
            {
                parts = parameters;
            } 
            Message msg = new OperationFormatterMessage(this, messageVersion,
                action == null ? null : ActionHeader.Create(action, messageVersion.Addressing), 
                parts, null, true/*isRequest*/); 
            AddPropertiesToMessage(msg, requestDescription, parts);
            AddHeadersToMessage(msg, requestDescription, parts, true /*isRequest*/); 

            return msg;
        }
 
        public Message SerializeReply(MessageVersion messageVersion, object[] parameters, object result)
        { 
            object[] parts = null; 
            object resultPart = null;
 
            if (messageVersion == null)
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("messageVersion");

            if (parameters == null) 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("parameters");
 
            if (replyDescription.IsTypedMessage) 
            {
                // If the response is a typed message then it must 
                // me the response (as opposed to an out param).  We will
                // serialize the response in the exact same way that we
                // would serialize a bunch of outs (with no return value).
 
                TypedMessageParts typedMessageParts = new TypedMessageParts(result, replyDescription);
 
                // make a copy of the list so that we have the actual values of the field/properties 
                parts = new object[typedMessageParts.Count];
                typedMessageParts.GetTypedMessageParts(parts); 

                resultPart = null;
            }
            else 
            {
                parts = parameters; 
                resultPart = result; 
            }
 
            Message msg = new OperationFormatterMessage(this, messageVersion,
                replyAction == null ? null : ActionHeader.Create(replyAction, messageVersion.Addressing),
                parts, resultPart, false/*isRequest*/);
            AddPropertiesToMessage(msg, replyDescription, parts); 
            AddHeadersToMessage(msg, replyDescription, parts, false /*isRequest*/);
            return msg; 
        } 

        void SerializeBodyContents(XmlDictionaryWriter writer, MessageVersion version, object[] parameters, object returnValue, bool isRequest) 
        {

            string action;
            MessageDescription messageDescription; 
            StreamFormatter streamFormatter;
            if(isRequest) 
            { 
                streamFormatter = requestStreamFormatter;
                action = RequestAction; 
                messageDescription = requestDescription;
            }
            else
            { 
                streamFormatter = replyStreamFormatter;
                action = ReplyAction; 
                messageDescription = replyDescription; 
            }
            if (streamFormatter != null) 
            {
                streamFormatter.Serialize(writer, parameters, returnValue);
                return;
            } 
            SerializeBody(writer, version, RequestAction, messageDescription, returnValue, parameters, isRequest);
        } 
 
        void AddPropertiesToMessage(Message message, MessageDescription messageDescription, object[] parameters)
        { 
            if (messageDescription.Properties.Count > 0)
            {
                AddPropertiesToMessageCore(message, messageDescription, parameters);
            } 
        }
 
        void AddPropertiesToMessageCore(Message message, MessageDescription messageDescription, object[] parameters) 
        {
            MessageProperties properties = message.Properties; 
            MessagePropertyDescriptionCollection propertyDescriptions = messageDescription.Properties;
            for (int i = 0; i < propertyDescriptions.Count; i++)
            {
                MessagePropertyDescription propertyDescription = propertyDescriptions[i]; 
                object parameter = parameters[propertyDescription.Index];
                if (null != parameter) 
                    properties.Add(propertyDescription.Name, parameter); 
            }
        } 

        void GetPropertiesFromMessage(Message message, MessageDescription messageDescription, object[] parameters)
        {
            if (messageDescription.Properties.Count > 0) 
            {
                GetPropertiesFromMessageCore(message, messageDescription, parameters); 
            } 
        }
 
        void GetPropertiesFromMessageCore(Message message, MessageDescription messageDescription, object[] parameters)
        {
            MessageProperties properties = message.Properties;
            MessagePropertyDescriptionCollection propertyDescriptions = messageDescription.Properties; 
            for (int i = 0; i < propertyDescriptions.Count; i++)
            { 
                MessagePropertyDescription propertyDescription = propertyDescriptions[i]; 
                if (properties.ContainsKey(propertyDescription.Name))
                { 
                    parameters[propertyDescription.Index] = properties[propertyDescription.Name];
                }
            }
        } 

        internal static object GetContentOfMessageHeaderOfT(MessageHeaderDescription headerDescription, object parameterValue, out bool mustUnderstand, out bool relay, out string actor) 
        { 
            actor = headerDescription.Actor;
            mustUnderstand = headerDescription.MustUnderstand; 
            relay = headerDescription.Relay;

            if (headerDescription.TypedHeader && parameterValue != null)
                parameterValue = TypedHeaderManager.GetContent(headerDescription.Type, parameterValue, out mustUnderstand, out relay, out actor); 
            return parameterValue;
        } 
 
        internal static bool IsValidReturnValue(MessagePartDescription returnValue)
        { 
            return (returnValue != null) && (returnValue.Type != typeof(void));
        }

        internal static XmlDictionaryString AddToDictionary(XmlDictionary dictionary, string s) 
        {
            XmlDictionaryString dictionaryString; 
            if (!dictionary.TryLookup(s, out dictionaryString)) 
            {
                dictionaryString = dictionary.Add(s); 
            }
            return dictionaryString;
        }
 
        internal static void Validate(OperationDescription operation, bool isRpc, bool isEncoded)
        { 
            if (isEncoded && !isRpc) 
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.SFxDocEncodedNotSupported, operation.Name))); 
            }

            bool hasVoid = false;
            bool hasTypedOrUntypedMessage = false; 
            bool hasParameter = false;
            for (int i = 0; i < operation.Messages.Count; i++) 
            { 
                MessageDescription message = operation.Messages[i];
                if (message.IsTypedMessage || message.IsUntypedMessage) 
                {
                    if (isRpc && operation.IsValidateRpcWrapperName)
                    {
                        if (!isEncoded) 
                            throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.SFxTypedMessageCannotBeRpcLiteral, operation.Name)));
 
                    } 
                    hasTypedOrUntypedMessage = true;
                } 
                else if (message.IsVoid)
                    hasVoid = true;
                else
                    hasParameter = true; 
            }
            if (hasParameter && hasTypedOrUntypedMessage) 
               throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.SFxTypedOrUntypedMessageCannotBeMixedWithParameters, operation.Name))); 
            if (isRpc && hasTypedOrUntypedMessage && hasVoid)
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.SFxTypedOrUntypedMessageCannotBeMixedWithVoidInRpc, operation.Name))); 
        }

        internal static void GetActions(OperationDescription description, XmlDictionary dictionary, out XmlDictionaryString action, out XmlDictionaryString replyAction)
        { 
            string actionString, replyActionString;
            actionString = description.Messages[0].Action; 
            if (actionString == MessageHeaders.WildcardAction) 
                actionString = null;
            if (!description.IsOneWay) 
                replyActionString = description.Messages[1].Action;
            else
                replyActionString = null;
            if (replyActionString == MessageHeaders.WildcardAction) 
                replyActionString = null;
            action = replyAction = null; 
            if (actionString != null) 
                action = AddToDictionary(dictionary, actionString);
            if (replyActionString != null) 
                replyAction = AddToDictionary(dictionary, replyActionString);
        }

        internal static NetDispatcherFaultException CreateDeserializationFailedFault(string reason, Exception innerException) 
        {
            reason = SR.GetString(SR.SFxDeserializationFailed1, reason); 
            FaultCode code = new FaultCode(FaultCodeConstants.Codes.DeserializationFailed, FaultCodeConstants.Namespaces.NetDispatch); 
            code = FaultCode.CreateSenderFaultCode(code);
            return new NetDispatcherFaultException(reason, code, innerException); 
        }

        internal static void TraceAndSkipElement(XmlReader xmlReader)
        { 
            if (DiagnosticUtility.ShouldTraceVerbose)
                DiagnosticUtility.DiagnosticTrace.TraceEvent(TraceEventType.Verbose, TraceCode.ElementIgnored, SR.GetString(SR.SFxTraceCodeElementIgnored), new StringTraceRecord("Element", xmlReader.NamespaceURI + ":" + xmlReader.LocalName)); 
            xmlReader.Skip(); 
        }
 
        class TypedMessageParts
        {
            object instance;
            MemberInfo[] members; 

            public TypedMessageParts(object instance, MessageDescription description) 
            { 
                if (description == null) throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("description"));
                if (instance == null) throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException(SR.GetString(SR.SFxTypedMessageCannotBeNull, description.Action))); 

                members = new MemberInfo[description.Body.Parts.Count + description.Properties.Count + description.Headers.Count];

                foreach (MessagePartDescription part in description.Headers) 
                    members[part.Index] = part.MemberInfo;
 
                foreach (MessagePartDescription part in description.Properties) 
                    members[part.Index] = part.MemberInfo;
 
                foreach (MessagePartDescription part in description.Body.Parts)
                    members[part.Index] = part.MemberInfo;

                this.instance = instance; 
            }
 
            object GetValue(int index) 
            {
                MemberInfo memberInfo = members[index]; 
                if (memberInfo.MemberType == MemberTypes.Property)
                {
                    return ((PropertyInfo)members[index]).GetValue(instance, null);
                } 
                else
                { 
                    return ((FieldInfo)members[index]).GetValue(instance); 
                }
            } 

            void SetValue(object value, int index)
            {
                MemberInfo memberInfo = members[index]; 
                if (memberInfo.MemberType == MemberTypes.Property)
                { 
                    ((PropertyInfo)members[index]).SetValue(instance, value, null); 
                }
                else 
                {
                    ((FieldInfo)members[index]).SetValue(instance, value);
                }
            } 

            internal void GetTypedMessageParts(object[] values) 
            { 
                for (int i = 0; i < this.members.Length; i++)
                { 
                    values[i] = GetValue(i);
                }
            }
 
            internal void SetTypedMessageParts(object[] values)
            { 
                for (int i = 0; i < this.members.Length; i++) 
                {
                    SetValue(values[i], i); 
                }
            }

            internal int Count 
            {
                get { return this.members.Length; } 
            } 
        }
 
        internal class OperationFormatterMessage : BodyWriterMessage
        {
            OperationFormatter operationFormatter;
             public OperationFormatterMessage(OperationFormatter operationFormatter, MessageVersion version, ActionHeader action, 
                object[] parameters, object returnValue, bool isRequest)
                 : base(version, action, new OperationFormatterBodyWriter(operationFormatter, version, parameters, returnValue, isRequest)) 
            { 
                this.operationFormatter = operationFormatter;
            } 


            public OperationFormatterMessage(MessageVersion version, string action, BodyWriter bodyWriter):base(version, action, bodyWriter){}
 
            OperationFormatterMessage(MessageHeaders headers, KeyValuePair[] properties, OperationFormatterBodyWriter bodyWriter)
            : base(headers, properties, bodyWriter) 
            { 
                operationFormatter = bodyWriter.OperationFormatter;
            } 

            protected override void OnWriteStartBody(XmlDictionaryWriter writer)
            {
                base.OnWriteStartBody(writer); 
                operationFormatter.WriteBodyAttributes(writer, this.Version);
            } 
 
            protected override MessageBuffer OnCreateBufferedCopy(int maxBufferSize)
            { 
                BodyWriter bufferedBodyWriter;
                if (BodyWriter.IsBuffered)
                {
                    bufferedBodyWriter = base.BodyWriter; 
                }
                else 
                { 
                    bufferedBodyWriter = base.BodyWriter.CreateBufferedCopy(maxBufferSize);
                } 
                KeyValuePair[] properties = new KeyValuePair[base.Properties.Count];
                ((ICollection>)base.Properties).CopyTo(properties, 0);
                return new OperationFormatterMessageBuffer(base.Headers, properties, bufferedBodyWriter);
            } 

            class OperationFormatterBodyWriter : BodyWriter 
            { 
                bool isRequest;
                OperationFormatter operationFormatter; 
                object[] parameters;
                object returnValue;
                MessageVersion version;
 
                public OperationFormatterBodyWriter(OperationFormatter operationFormatter, MessageVersion version,
                    object[] parameters, object returnValue, bool isRequest) 
                    : base(AreParametersBuffered(isRequest, operationFormatter)) 
                {
                    this.parameters = parameters; 
                    this.returnValue = returnValue;
                    this.isRequest = isRequest;
                    this.operationFormatter = operationFormatter;
                    this.version = version; 
                }
 
                object ThisLock 
                {
                    get { return this; } 
                }

                static bool AreParametersBuffered(bool isRequest, OperationFormatter operationFormatter)
                { 
                    StreamFormatter streamFormatter = isRequest ? operationFormatter.requestStreamFormatter : operationFormatter.replyStreamFormatter;
                    return streamFormatter == null; 
                } 

                protected override void OnWriteBodyContents(XmlDictionaryWriter writer) 
                {
                    lock (ThisLock)
                    {
                        this.operationFormatter.SerializeBodyContents(writer, this.version, this.parameters, this.returnValue, this.isRequest); 
                    }
                } 
 
                internal OperationFormatter OperationFormatter
                { 
                    get { return operationFormatter; }
                }
            }
 
            class OperationFormatterMessageBuffer : BodyWriterMessageBuffer
            { 
                public OperationFormatterMessageBuffer(MessageHeaders headers, 
                    KeyValuePair[] properties, BodyWriter bodyWriter):base(headers, properties, bodyWriter)
                { 
                }

                public override Message CreateMessage()
                { 
                    OperationFormatterBodyWriter operationFormatterBodyWriter = base.BodyWriter as OperationFormatterBodyWriter;
                    if (operationFormatterBodyWriter == null) 
                        return base.CreateMessage(); 
                    lock (ThisLock)
                    { 
                        if (base.Closed)
                            throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(CreateBufferDisposedException());
                        return new OperationFormatterMessage(base.Headers, base.Properties, operationFormatterBodyWriter);
                    } 
                }
            } 
        } 

        internal abstract class OperationFormatterHeader : MessageHeader 
        {
            protected MessageHeader innerHeader;//use innerHeader to handle versionSupported, actor/role handling etc.
            protected OperationFormatter operationFormatter;
            protected MessageVersion version; 

            public OperationFormatterHeader(OperationFormatter operationFormatter, MessageVersion version, string name, string ns, bool mustUnderstand, string actor, bool relay) 
            { 
                this.operationFormatter = operationFormatter;
                this.version = version; 
                if (actor != null)
                    innerHeader = MessageHeader.CreateHeader(name, ns, null/*headerValue*/, mustUnderstand, actor, relay);
                else
                    innerHeader = MessageHeader.CreateHeader(name, ns, null/*headerValue*/,mustUnderstand, "", relay); 
            }
 
 
            public override bool IsMessageVersionSupported(MessageVersion messageVersion)
            { 
                return innerHeader.IsMessageVersionSupported(messageVersion);
            }

 
            public override string Name
            { 
                get { return innerHeader.Name; } 
            }
 
            public override string Namespace
            {
                get { return innerHeader.Namespace; }
            } 

            public override bool MustUnderstand 
            { 
                get { return innerHeader.MustUnderstand; }
            } 

            public override bool Relay
            {
                get { return innerHeader.Relay; } 
            }
 
            public override string Actor 
            {
                get { return innerHeader.Actor; } 
            }

            protected override void OnWriteStartHeader(XmlDictionaryWriter writer, MessageVersion messageVersion)
            { 
                //Prefix needed since there may be xsi:type attribute at toplevel with qname value where ns = ""
                writer.WriteStartElement((this.Namespace == null || this.Namespace.Length == 0) ? string.Empty : "h", this.Name, this.Namespace); 
                OnWriteHeaderAttributes(writer, messageVersion); 
            }
 
            protected virtual void OnWriteHeaderAttributes(XmlDictionaryWriter writer, MessageVersion messageVersion)
            {
                base.WriteHeaderAttributes(writer, messageVersion);
            } 
        }
 
        internal class XmlElementMessageHeader:OperationFormatterHeader 
        {
            protected XmlElement headerValue; 
            public XmlElementMessageHeader(OperationFormatter operationFormatter, MessageVersion version, string name, string ns, bool mustUnderstand, string actor, bool relay, XmlElement headerValue):
                base(operationFormatter, version, name, ns, mustUnderstand, actor, relay)
                {
                    this.headerValue = headerValue; 
                }
 
            protected override void OnWriteHeaderAttributes(XmlDictionaryWriter writer, MessageVersion messageVersion) 
            {
                base.WriteHeaderAttributes(writer, messageVersion); 
                XmlDictionaryReader nodeReader = XmlDictionaryReader.CreateDictionaryReader(new XmlNodeReader(headerValue));
                nodeReader.MoveToContent();
                writer.WriteAttributes(nodeReader, false);
            } 

            protected override void OnWriteHeaderContents(XmlDictionaryWriter writer, MessageVersion messageVersion) 
            { 
                headerValue.WriteContentTo(writer);
            } 
        }
        internal struct QName
        {
            internal string Name; 
            internal string Namespace;
            internal QName(string name, string ns) 
            { 
                Name = name;
                Namespace = ns; 
            }
        }
        internal class QNameComparer : IEqualityComparer
        { 
            static internal QNameComparer Singleton = new QNameComparer();
            QNameComparer(){} 
 
            public bool  Equals(QName x, QName y)
            { 
 	            return x.Name == y.Name && x.Namespace == y.Namespace;
            }

            public int  GetHashCode(QName obj) 
            {
	            return obj.Name.GetHashCode(); 
            } 
        }
        internal class MessageHeaderDescriptionTable : Dictionary 
        {
            internal MessageHeaderDescriptionTable() : base(QNameComparer.Singleton) { }
            internal void Add(string name, string ns, MessageHeaderDescription message)
            { 
                base.Add(new QName(name, ns), message);
            } 
            internal MessageHeaderDescription Get(string name, string ns) 
            {
                MessageHeaderDescription message; 
                if (base.TryGetValue(new QName(name, ns), out message))
                    return message;
                return null;
            } 
        }
    } 
} 

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.


                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK