如何在 C# 中解析 MTOM soap 响应
How to parse MTOM soap response in c#
我想解析 soap MTOM 格式的 Web 服务响应。
是回应
--MIMEBoundary_437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0
Content - Type: application / xop + xml; charset = utf - 8; type = "text/xml"
Content - Transfer - Encoding: binary
Content - ID: < 0.737235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0 @apache.org >
<? xml version = "1.0" encoding = "utf-8" ?>
< soapenv : Envelope xmlns: soapenv = "http://schemas.xmlsoap.org/soap/envelope/" >
< soapenv:Body >
< sendDataResponse xmlns: a = "http://www.w3.org/2005/05/xmlmime" xmlns = "http://org/emedny/fts/" >
< output >< fileName > ABC.x12 </ fileName ></ output >
</ sendDataResponse >
</ soapenv:Body >
</ soapenv:Envelope >
--MIMEBoundary_437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0--
我试过使用 XmlDictionaryReader 但它出错了
"The Message Transmission Optimization Mechanism (MTOM) message encoding is not supported on this platform."
string MTOM = response;
MemoryStream ms;
ItemOperations obj;
DataContractSerializer dcs = new DataContractSerializer(typeof(ItemOperations));
string fixedMtom = MTOM.Replace(
"Multipart/Related;boundary=437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0;",
"Multipart/Related;boundary=\"437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0?MTOM\";");
ms = new MemoryStream(Encoding.UTF8.GetBytes(fixedMtom));
XmlDictionaryReader reader = XmlDictionaryReader.CreateMtomReader(ms, Encoding.UTF8, XmlDictionaryReaderQuotas.Max);
我想从 soap 中提取文件名element.How我能得到吗?
使用 VS 解析 xml 结构(Edit/Paste 作为 json 或 xml)或 enter link description here
[XmlRoot(ElementName = "output", Namespace = "http://org/emedny/fts/")]
public class Output
{
[XmlElement(ElementName = "fileName", Namespace = "http://org/emedny/fts/")]
public string FileName { get; set; }
}
[XmlRoot(ElementName = "sendDataResponse", Namespace = "http://org/emedny/fts/")]
public class SendDataResponse
{
[XmlElement(ElementName = "output", Namespace = "http://org/emedny/fts/")]
public Output Output { get; set; }
[XmlAttribute(AttributeName = "a", Namespace = "http://www.w3.org/2000/xmlns/")]
public string A { get; set; }
[XmlAttribute(AttributeName = "xmlns")]
public string Xmlns { get; set; }
}
[XmlRoot(ElementName = "Body", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public class Body
{
[XmlElement(ElementName = "sendDataResponse", Namespace = "http://org/emedny/fts/")]
public SendDataResponse SendDataResponse { get; set; }
}
[XmlRoot(ElementName = "Envelope", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public class Envelope
{
[XmlElement(ElementName = "Body", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public Body Body { get; set; }
[XmlAttribute(AttributeName = "soapenv", Namespace = "http://www.w3.org/2000/xmlns/")]
public string Soapenv { get; set; }
}
.....
using (var st = File.OpenRead(@"i_saved_your_request_here.xml"))
{
var data = new XmlSerializer(typeof(Envelope)).Deserialize(st) as Envelope;
var output = data.Body.SendDataResponse.Output.FileName;
}
我终于使用 Regex 让它工作了。 xml 中 space 的问题丢失:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
using System.IO;
using System.Text.RegularExpressions;
namespace ConsoleApplication117
{
class Program
{
const string FILENAME = @"c:\temp\test.txt";
static void Main(string[] args)
{
string input = File.ReadAllText(FILENAME);
string pattern = @"(?'xml'\<\?.*)--MIMEBoundary";
Match match = Regex.Match(input,pattern,RegexOptions.Singleline);
string xml = match.Groups["xml"].Value.Trim();
string pattern1 = @"\<[?/]?((\s*\w+\s*:\s*\w+)|(\s*\w+))";
xml = Regex.Replace(xml, pattern1, ReplaceSpaces);
string pattern2 = @"\w+\s*:\s*\w+\s*=";
xml = Regex.Replace(xml, pattern2, ReplaceSpaces); //remove spaces in namespaces
XDocument doc = XDocument.Parse(xml);
string filename = (string)doc.Descendants().Where(x => x.Name.LocalName == "fileName").FirstOrDefault();
}
static string ReplaceSpaces(Match match)
{
string input = match.Value;
string pattern = @"\s*(?'name1'\w+)\s*(?'colon':)*\s*(?'name2'\w*)";
string output = Regex.Replace(input, pattern, "${name1}${colon}${name2}");
return output;
}
}
public class Player
{
}
}
我想解析 soap MTOM 格式的 Web 服务响应。 是回应
--MIMEBoundary_437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0
Content - Type: application / xop + xml; charset = utf - 8; type = "text/xml"
Content - Transfer - Encoding: binary
Content - ID: < 0.737235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0 @apache.org >
<? xml version = "1.0" encoding = "utf-8" ?>
< soapenv : Envelope xmlns: soapenv = "http://schemas.xmlsoap.org/soap/envelope/" >
< soapenv:Body >
< sendDataResponse xmlns: a = "http://www.w3.org/2005/05/xmlmime" xmlns = "http://org/emedny/fts/" >
< output >< fileName > ABC.x12 </ fileName ></ output >
</ sendDataResponse >
</ soapenv:Body >
</ soapenv:Envelope >
--MIMEBoundary_437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0--
我试过使用 XmlDictionaryReader 但它出错了 "The Message Transmission Optimization Mechanism (MTOM) message encoding is not supported on this platform."
string MTOM = response;
MemoryStream ms;
ItemOperations obj;
DataContractSerializer dcs = new DataContractSerializer(typeof(ItemOperations));
string fixedMtom = MTOM.Replace(
"Multipart/Related;boundary=437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0;",
"Multipart/Related;boundary=\"437235bf25f089af96e3a1387b60bdfbd52e58e56b20f9b0?MTOM\";");
ms = new MemoryStream(Encoding.UTF8.GetBytes(fixedMtom));
XmlDictionaryReader reader = XmlDictionaryReader.CreateMtomReader(ms, Encoding.UTF8, XmlDictionaryReaderQuotas.Max);
我想从 soap 中提取文件名element.How我能得到吗?
使用 VS 解析 xml 结构(Edit/Paste 作为 json 或 xml)或 enter link description here
[XmlRoot(ElementName = "output", Namespace = "http://org/emedny/fts/")]
public class Output
{
[XmlElement(ElementName = "fileName", Namespace = "http://org/emedny/fts/")]
public string FileName { get; set; }
}
[XmlRoot(ElementName = "sendDataResponse", Namespace = "http://org/emedny/fts/")]
public class SendDataResponse
{
[XmlElement(ElementName = "output", Namespace = "http://org/emedny/fts/")]
public Output Output { get; set; }
[XmlAttribute(AttributeName = "a", Namespace = "http://www.w3.org/2000/xmlns/")]
public string A { get; set; }
[XmlAttribute(AttributeName = "xmlns")]
public string Xmlns { get; set; }
}
[XmlRoot(ElementName = "Body", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public class Body
{
[XmlElement(ElementName = "sendDataResponse", Namespace = "http://org/emedny/fts/")]
public SendDataResponse SendDataResponse { get; set; }
}
[XmlRoot(ElementName = "Envelope", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public class Envelope
{
[XmlElement(ElementName = "Body", Namespace = "http://schemas.xmlsoap.org/soap/envelope/")]
public Body Body { get; set; }
[XmlAttribute(AttributeName = "soapenv", Namespace = "http://www.w3.org/2000/xmlns/")]
public string Soapenv { get; set; }
}
.....
using (var st = File.OpenRead(@"i_saved_your_request_here.xml"))
{
var data = new XmlSerializer(typeof(Envelope)).Deserialize(st) as Envelope;
var output = data.Body.SendDataResponse.Output.FileName;
}
我终于使用 Regex 让它工作了。 xml 中 space 的问题丢失:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
using System.IO;
using System.Text.RegularExpressions;
namespace ConsoleApplication117
{
class Program
{
const string FILENAME = @"c:\temp\test.txt";
static void Main(string[] args)
{
string input = File.ReadAllText(FILENAME);
string pattern = @"(?'xml'\<\?.*)--MIMEBoundary";
Match match = Regex.Match(input,pattern,RegexOptions.Singleline);
string xml = match.Groups["xml"].Value.Trim();
string pattern1 = @"\<[?/]?((\s*\w+\s*:\s*\w+)|(\s*\w+))";
xml = Regex.Replace(xml, pattern1, ReplaceSpaces);
string pattern2 = @"\w+\s*:\s*\w+\s*=";
xml = Regex.Replace(xml, pattern2, ReplaceSpaces); //remove spaces in namespaces
XDocument doc = XDocument.Parse(xml);
string filename = (string)doc.Descendants().Where(x => x.Name.LocalName == "fileName").FirstOrDefault();
}
static string ReplaceSpaces(Match match)
{
string input = match.Value;
string pattern = @"\s*(?'name1'\w+)\s*(?'colon':)*\s*(?'name2'\w*)";
string output = Regex.Replace(input, pattern, "${name1}${colon}${name2}");
return output;
}
}
public class Player
{
}
}