Ricerche XPath su messaggi SOAP con WCF
A volte capita di avere bisogno di implementare servizi WCF che lavorino direttamente con il Message (System.ServiceModel.Channels.Message) a basso livello.
Ad esempio può servire per creare SOAP Router o SOAP Intermediaries. In questi casi le ricerche XPath sul messaggio SOAP devono avvenire usando anche i vari namespace di SOAP, WS-Security, WS-Addressing, ecc. a seconda dei casi.
In questi situazioni, al di là di utilizzare un XPathNavigator, o qualcosa di equivalente, sul messaggio XML diventa anche fondamentale avere un XmlNamespaceManager correttamente configurato per riconoscere i vari Namespace XML delle specifiche di cui sopra. Ebbene in WCF esiste già una classe pensata ad hoc. Si trova in System.ServiceModel.Dispatcher e si chiama XPathMessageContext.
Ecco come utilizzarla, ad esempio per estrarre il SOAP Body ("/s12:Envelope/s12:Body", dove s12 è il prefisso usato per SOAP 1.2) con tutto il suo contenuto:
XmlNamespaceManager nsManager = new XPathMessageContext();
XPathExpression soapBodyExpression = XPathExpression.Compile("/s12:Envelope/s12:Body", nsManager);
XmlDocument xmlMessage = new XmlDocument();
xmlMessage.LoadXml(message.ToString());
XPathNavigator messageNavigator = xmlMessage.CreateNavigator();
XPathNodeIterator messageBodyIterator = messageNavigator.Select(soapBodyExpression);
if (messageBodyIterator.Count > 0)
{
if (messageBodyIterator.MoveNext())
{
// Scrive a Console il tag SOAP:Body e tutto il suo contenuto
Console.WriteLine(messageBodyIterator.Current.OuterXml);
}
}
N.B.: La classe deriva da XsltContext, quindi può risultare utile anche nelle trasformazioni XSLT dei messaggi SOAP.