public static XmlReader ParseSoapMessage(byte[] soapMessage, out WsWsaHeader header) { MemoryStream requestStream = new MemoryStream(soapMessage); XmlReader reader = XmlReader.Create(requestStream); header = new WsWsaHeader(); try { reader.ReadStartElement("Envelope", WsWellKnownUri.SoapNamespaceUri); #if DEBUG int depth = reader.Depth; #endif header.ParseHeader(reader); #if DEBUG Microsoft.SPOT.Debug.Assert(XmlReaderHelper.HasReadCompleteNode(depth, reader)); #endif reader.ReadStartElement("Body", WsWellKnownUri.SoapNamespaceUri); } catch (XmlException e) { reader.Close(); throw new WsFaultException(header, WsFaultType.XmlException, e.ToString()); } return reader; }
/// <summary> /// Processes a message /// </summary> /// <param name="stream">The message being processed.</param> /// <param name="ctx">The context associated with the message.</param> /// <returns>The handling status for this operation.</returns> protected override ChainResult OnProcessInputMessage(ref WsMessage msg, BindingContext ctx) { if(msg == null) return ChainResult.Abort; ArrayList props = ctx.BindingProperties; if (props != null) { int len = props.Count; for (int j = 0; j < len; j++) { BindingProperty prop = (BindingProperty)props[j]; if (prop.Name == HttpKnownHeaderNames.ContentType) { string strContentType = ((string)prop.Value).ToLower(); if (strContentType.IndexOf("multipart/related;") == 0) { // Create the mtom header class msg.MtomPropeties = new WsMtomParams(); // Parse Mtom Content-Type parameters string[] fields = strContentType.Substring(18).Split(';'); int fieldsLen = fields.Length; for (int i = 0; i < fieldsLen; ++i) { string type = fields[i]; int idx = type.IndexOf('='); if(idx != -1) { string param = type.Substring(0, idx).Trim(); string value = type.Substring(idx + 1).Trim('\"'); switch (param.ToUpper()) { case "BOUNDARY": if (param.Length > 72) throw new ArgumentException("Mime boundary element length exceeded.", "boundary"); msg.MtomPropeties.boundary = value; break; case "TYPE": msg.MtomPropeties.type = value; break; case "START": msg.MtomPropeties.start = value; break; case "START-INFO": msg.MtomPropeties.startInfo = value; break; default: break; } } } // Check required Mtom fields if (msg.MtomPropeties.boundary == null || msg.MtomPropeties.type == null || msg.MtomPropeties.start == null) { throw new WsFaultException(msg.Header, WsFaultType.WseInvalidMessage); } WsMtom mtom = new WsMtom((byte[])msg.Body); msg.Body = mtom.ParseMessage(msg.MtomPropeties.boundary); msg.BodyParts = mtom.BodyParts; } else if (strContentType.IndexOf("application/soap+xml") != 0) { throw new WsFaultException(msg.Header, WsFaultType.WseInvalidMessage); } } } } if (msg.Body == null) return ChainResult.Continue; MemoryStream requestStream = new MemoryStream((byte[])msg.Body); XmlReader reader = XmlReader.Create(requestStream); WsWsaHeader hdr = new WsWsaHeader(); reader.ReadStartElement("Envelope", WsWellKnownUri.SoapNamespaceUri); if(ctx.Version.IncludeSoapHeaders) { hdr.ParseHeader(reader, ctx.Version); } msg.Header = hdr; reader.ReadStartElement("Body", WsWellKnownUri.SoapNamespaceUri); if(msg.Deserializer != null) { msg.Body = ((DataContractSerializer)msg.Deserializer).ReadObject(reader); reader.Dispose(); } else { msg.Reader = reader; } return ChainResult.Continue; }