WSO2 ESB - 在负载的标记内使用XML数据调用Webservices

问题描述:

我需要通过中间件调用外部Web服务,其中一个包含嵌入式XML的有效内容中的标记。下面的示例负载和序列片段。我遇到以下问题。场景1:(第24行)表达式=“get-property('PayloadXML')” - 发出发送命令后,Web服务方法无法识别。场景2 :(第24行)表达式=“get-property('lPayload')” - 发出发送命令后,web服务方法成功调用。但是,对于目标系统成功处理消息,它需要处理CDATA元素(包装)。WSO2 ESB - 在负载的标记内使用XML数据调用Webservices

当试图通过soapUI调用方案2时,该过程是成功的。从我研究的内容(Passing CDATA in WSO2),在转发消息之前,soapUI似乎在内部处理CDATA元素。

现在,我明白我设置的方式情景2并不理想(更多的是黑客),但我不知道有任何其他方式来实现这一点。我已经阅读了许多博客/文章,并尝试通过XSLT中介转换(开发)Payload而没有运气。我也遇到了以下帖子http://www.yenlo.com/en/how-to-preserve-a-cdata-in-xml-that-is-circulating-in-a-wso2-enterprise-service-bus/,但我似乎无法找到正在引用的修补程序。

所以我的问题如下: 1.是否有任何其他方式/机制来达到我的要求? 2. WSO2 ESB 4.9.0版本能否解决上述问题?

样品载荷:

<sample><test>MyData</test></sample> 

序列段:

 <property xmlns:ns1="http://ws.wso2.org/dataservice" 
       xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" 
       name="PayloadXML" 
       expression="$body/data-services-event/content/ns1:return/ns1:return/ns1:PayLoadXML"/> 
    <property xmlns:ns="http://org.apache.synapse/xsd" 
       name="lPayload" 
       expression="fn:concat(fn:concat('&lt;![CDATA[',get-property('PayloadXML')), ']]&gt;')"/> 
    <payloadFactory media-type="xml"> 
     <format> 
      <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" 
          xmlns:log="http://mynamespace"> 
       <soapenv:Header/> 
       <soapenv:Body> 
       <log:publishMessage> 
        <Payload xmlns="">$1</Payload> 
       </log:publishMessage> 
       </soapenv:Body> 
      </soapenv:Envelope> 
     </format> 
     <args> 
      <arg xmlns:ns2="http://org.apache.synapse/xsd" 
       xmlns:ns="http://org.apache.synapse/xsd" 
       evaluator="xml" 
       expression="get-property('lPayload')"/> 
     </args> 
    </payloadFactory> 

下面是接收的XML数据并发送回一个新的XML消息与输入内容的一个子部分的样品的代理服务一个CDATA部分。

发送:

<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"> 
    <SOAP-ENV:Body> 
     <PayloadXML> 
      <sample><test>MyData</test></sample> 
     </PayloadXML> 
    </SOAP-ENV:Body> 
</SOAP-ENV:Envelope> 

您会收到:

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"> 
    <soapenv:Header/> 
    <soapenv:Body> 
     <log:publishMessage xmlns:log="http://mynamespace"> 
      <Payload><![CDATA[<sample><test>MyData</test></sample>]]></Payload> 
     </log:publishMessage> 
    </soapenv:Body> 
</soapenv:Envelope> 

代理DEF:

<?xml version="1.0" encoding="UTF-8"?> 
<proxy xmlns="http://ws.apache.org/ns/synapse" name="TestSOF" transports="http" statistics="disable" trace="disable" startOnLoad="true"> 
    <target> 
     <inSequence> 
      <!-- extract xml content from the input message --> 
      <property name="xmlContent" expression="$body/PayloadXML/*[1]" type="OM"/> 
      <!-- compose a new message --> 
      <enrich> 
       <source type="inline" clone="true"> 
        <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"> 
         <soapenv:Header/> 
         <soapenv:Body> 
          <log:publishMessage xmlns:log="http://mynamespace"> 
           <Payload xmlns=""/> 
          </log:publishMessage> 
         </soapenv:Body> 
        </soapenv:Envelope> 
       </source> 
       <target type="envelope"/> 
      </enrich> 
      <!-- create a CDATA section for 'Payload' node --> 
      <script language="js"> 
       importPackage(Packages.org.apache.axiom.om); 
       var payloadElmt = mc.getEnvelope().getBody().getFirstElement().getFirstElement(); 
       var omText = payloadElmt.getOMFactory().createOMText(payloadElmt, mc.getProperty("xmlContent"), OMNode.CDATA_SECTION_NODE); 
       payloadElmt.addChild(omText)      
      </script> 
      <!-- send back this new message as a response for the caller --> 
      <header name="To" action="remove"/> 
      <property name="RESPONSE" value="true"/> 
      <property name="NO_ENTITY_BODY" scope="axis2" action="remove"/> 
      <send/> 
     </inSequence> 
    </target> 
    <description/> 
</proxy> 
+0

如果用了SoapUI测试,看看RAW格式 –

+0

嗨让 - 响应米歇尔,感谢您的及时回应和解决方案。我将其改编成我的用例,并且运行得非常出色。非常感激... – MrT

如果你的基本要求是标签内通过XML数据,这是这是一个例子。

这里我使用的是wso2 ESB 4.9.0。基本的是,您需要将有效载荷工厂格式存储在注册表中,并在有效载荷工厂配置中使用它作为波纹管。

<proxy xmlns="http://ws.apache.org/ns/synapse" 
    name="foo" 
    transports="https,http" 
    statistics="disable" 
    trace="disable" 
    startOnLoad="true"> 
<target> 
    <inSequence> 
     <property xmlns:ns="http://org.apache.synapse/xsd" 
        name="Request" 
        expression="$body/child::*[fn:position()=1]" 
        scope="default" 
        type="STRING"/> 
     <payloadFactory media-type="xml"> 
      <format key="conf:/repository/esb/myPF"/> 
      <args> 
       <arg evaluator="xml" expression="$ctx:Request"/> 
       <arg value="1"/> 
      </args> 
     </payloadFactory> 

     <send> 
      <endpoint> 
       <address uri="http://127.0.0.1:9763/services/Hello"/> 
      </endpoint> 
     </send> 
    </inSequence> 
    <outSequence> 
     <send/> 
    </outSequence> 
</target> 
<description/> 

以上就是我的代理服务。我从ESB获取客户端请求中获取第一个子进程,并将其用作有效负载工厂调解器的输入。

注册表资源的内容如下图所示。

<ns:testMethod xmlns:ns="http://example.com"> 
          <xs:xmlBody xmlns:xs="http://example.com"><![CDATA[$1]]></xs:xmlBody> 
          <xs:sessionId xmlns:xs="http://example.com">$2</xs:sessionId> 
         </ns:testMethod> 

您可以通过为ESB启用接线日志来测试场景[2]。

在这里我已经在WSO2 AS中托管了一个简单的axis2服务进行测试。这是wirelog输出。

[2016-02-24 19:02:24,696] DEBUG - wire << "POST /services/Hello HTTP/1.1[\r][\n]" 
[2016-02-24 19:02:24,696] DEBUG - wire << "Content-Type: application/soap+xml; charset=UTF-8; action="urn:mediate"[\r][\n]" 
[2016-02-24 19:02:24,696] DEBUG - wire << "Transfer-Encoding: chunked[\r][\n]" 
[2016-02-24 19:02:24,696] DEBUG - wire << "Host: 127.0.0.1:9763[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "Connection: Keep-Alive[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "User-Agent: Synapse-PT-HttpComponents-NIO[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "180[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "<?xml version='1.0' encoding='UTF-8'?><soapenv:Envelope xmlns:soapenv="http://www.w3.org/2003/05/soap-envelope"><soapenv:Body><ns:testMethod xmlns:ns="http://example.com"><xs:xmlBody xmlns:xs="http://example.com"><![CDATA[<sample><test>MyData</test></sample>]]></xs:xmlBody><xs:sessionId xmlns:xs="http://example.com">1</xs:sessionId></ns:testMethod></soapenv:Body></soapenv:Envelope>[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "0[\r][\n]" 
[2016-02-24 19:02:24,697] DEBUG - wire << "[\r][\n]" 

在这里,你可以找到与内容类型定义注册表资源为text/xmlregistry resource

[2] https://docs.wso2.com/display/ESB490/Setting+Up+Logging