如何:c# XML InfoSet 到 JSON
How to: c# XML InfoSet to JSON
因此 WCF 采用 JSON,并且出于某种原因将其转换为 XML 信息集(参见:). It then reads back this XML Infoset internally using the JsonReaderDelegator (see: https://referencesource.microsoft.com/#System.Runtime.Serialization/System/Runtime/Serialization/Json/JsonReaderDelegator.cs,c0d6a87689227f04)。
我正在对 WCF 执行流程进行一些非常深入的修改,我需要将 XML 信息集反转回原来的 JSON。
.NET 或外部是否有库可以获取 WCF 生成的 XML 信息集并将其转换回其原始 JSON?
找到了一个在我的场景中有效的答案,只是做了一些有限的修改。
本文:https://blogs.msdn.microsoft.com/carlosfigueira/2011/04/18/wcf-extensibility-message-inspectors/ 解释了如何记录最初进入 WCF 的 JSON,即使它仅作为 XML InfoSet 公开。这是关键的见解。具体看它的MessageToString实现。
下面是我的代码的相关部分,基于上面 link、运行 中我编写的 class internal class MessageFormatInspector : IDispatchMessageInspector, IEndpointBehavior
中 MessageToString 的实现注入 WCF 堆栈:
public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
{
...
var s = GetJsonFromMessage(request);
...
}
private static string GetJsonFromMessage(ref Message request)
{
using (MemoryStream ms = new MemoryStream())
{
using (XmlDictionaryWriter writer = JsonReaderWriterFactory.CreateJsonWriter(ms))
{
request.WriteMessage(writer);
writer.Flush();
string json = Encoding.UTF8.GetString(ms.ToArray()); //extract the JSON at this point
//now let's make our copy of the message to support the WCF pattern of rebuilding messages after consuming the inner stream (see: https://msdn.microsoft.com/en-us/library/system.servicemodel.dispatcher.idispatchmessageinspector.afterreceiverequest(v=vs.110).aspx and https://blogs.msdn.microsoft.com/carlosfigueira/2011/05/02/wcf-extensibility-message-formatters/)
ms.Position = 0; //Rewind. We're about to make a copy and restore the message we just consumed.
XmlDictionaryReader reader = JsonReaderWriterFactory.CreateJsonReader(ms, XmlDictionaryReaderQuotas.Max); //since we used a JsonWriter, we read the data back, we need to use the correlary JsonReader.
Message restoredRequestCopy = Message.CreateMessage(reader, int.MaxValue, request.Version); //now after a lot of work, create the actual copy
restoredRequestCopy.Properties.CopyProperties(request.Properties); //copy over the properties
request = restoredRequestCopy;
return json;
}
}
}
遗憾的是,以上代码仅适用于 WCF 消息检查器的上下文。
但是,它可以使用具有 XML InfoSet 的 XMLDictionary,并使用 WCF 自己内置的 JsonWriter 来反转 WCF 所做的转换并发出原始 JSON.
我希望这可以帮助某人在将来节省一些时间。
因此 WCF 采用 JSON,并且出于某种原因将其转换为 XML 信息集(参见:). It then reads back this XML Infoset internally using the JsonReaderDelegator (see: https://referencesource.microsoft.com/#System.Runtime.Serialization/System/Runtime/Serialization/Json/JsonReaderDelegator.cs,c0d6a87689227f04)。
我正在对 WCF 执行流程进行一些非常深入的修改,我需要将 XML 信息集反转回原来的 JSON。
.NET 或外部是否有库可以获取 WCF 生成的 XML 信息集并将其转换回其原始 JSON?
找到了一个在我的场景中有效的答案,只是做了一些有限的修改。
本文:https://blogs.msdn.microsoft.com/carlosfigueira/2011/04/18/wcf-extensibility-message-inspectors/ 解释了如何记录最初进入 WCF 的 JSON,即使它仅作为 XML InfoSet 公开。这是关键的见解。具体看它的MessageToString实现。
下面是我的代码的相关部分,基于上面 link、运行 中我编写的 class internal class MessageFormatInspector : IDispatchMessageInspector, IEndpointBehavior
中 MessageToString 的实现注入 WCF 堆栈:
public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
{
...
var s = GetJsonFromMessage(request);
...
}
private static string GetJsonFromMessage(ref Message request)
{
using (MemoryStream ms = new MemoryStream())
{
using (XmlDictionaryWriter writer = JsonReaderWriterFactory.CreateJsonWriter(ms))
{
request.WriteMessage(writer);
writer.Flush();
string json = Encoding.UTF8.GetString(ms.ToArray()); //extract the JSON at this point
//now let's make our copy of the message to support the WCF pattern of rebuilding messages after consuming the inner stream (see: https://msdn.microsoft.com/en-us/library/system.servicemodel.dispatcher.idispatchmessageinspector.afterreceiverequest(v=vs.110).aspx and https://blogs.msdn.microsoft.com/carlosfigueira/2011/05/02/wcf-extensibility-message-formatters/)
ms.Position = 0; //Rewind. We're about to make a copy and restore the message we just consumed.
XmlDictionaryReader reader = JsonReaderWriterFactory.CreateJsonReader(ms, XmlDictionaryReaderQuotas.Max); //since we used a JsonWriter, we read the data back, we need to use the correlary JsonReader.
Message restoredRequestCopy = Message.CreateMessage(reader, int.MaxValue, request.Version); //now after a lot of work, create the actual copy
restoredRequestCopy.Properties.CopyProperties(request.Properties); //copy over the properties
request = restoredRequestCopy;
return json;
}
}
}
遗憾的是,以上代码仅适用于 WCF 消息检查器的上下文。
但是,它可以使用具有 XML InfoSet 的 XMLDictionary,并使用 WCF 自己内置的 JsonWriter 来反转 WCF 所做的转换并发出原始 JSON.
我希望这可以帮助某人在将来节省一些时间。