如何在Java SAAJ中用soap响应中的(<)替换(<)

时间:2015-11-02 11:04:13

标签: java soap cdata saaj

我有一个包含CDATA的soap响应,但是我在java中处理响应,所有开头引号(<)都替换为(<)。

以下是响应的样子

 <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
  <ns:Response xmlns:ns="http://pipeline_ws">
     <ns:return>
     <![CDATA[<fr><Result>
        <ListPartner>
            <operator>
                <country_code></country_code>
                <currency_code></currency_code>
                <operator_code></operator_code>

        </operator>
     </ListPartner>
 </Result></fr>]]></ns:return>
  </ns:Response>
</soapenv:Body>
</soapenv:Envelope>

但相反,这是我得到的回应

 <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
    <ns:Response xmlns:ns="http://pipeline_ws">
        <ns:return>
&lt;fr>
&lt;Result>
&lt;ListPartner>
&lt;operator>
&lt;country_code>&lt;/country_code>
&lt;currency_code>&lt;/currency_code>
&lt;operator_code>&lt;/operator_code>   
&lt;/operator>
&lt;/ListPartner>
&lt;/Result>
&lt;/fr>
    </ns:return>
</ns:Response>
</soapenv:Body>
</soapenv:Envelope>

请帮助提供删除/替换不需要的字符(&lt;)的解决方案,以便我可以解析响应。我正在使用SAAJ来处理响应

        // Process the SOAP Response
SOAPMessage soapResponse = soapConnection.call(createSOAPRequest(), url);
        soapResponse.writeTo(System.out);

1 个答案:

答案 0 :(得分:0)

解析XML并将<ns:return/>的文本节点值检索为字符串。然后,这个字符串可以被视为XML。

final XPath xpath = XPathFactory.newInstance().newXPath();
xpath.setNamespaceContext(new MyNamespaceContext());
final String xmlFile = "1.xml";
final InputSource source = new InputSource(new FileInputStream(xmlFile));

final DocumentBuilderFactory fac = DocumentBuilderFactory.newInstance();
fac.setNamespaceAware(true);
final Document doc = fac.newDocumentBuilder().parse(source);

final String result = (String) xpath.evaluate(
    "/soapenv:Envelope/soapenv:Body/pipeline:Response/pipeline:return/text()", 
    doc, XPathConstants.STRING);

System.out.println(result);

请注意,您应该在DocumentBuilderFactory实例中设置名称空间感知。

这里有一个简单的NamespaceContext实现,用于定义所需的名称空间前缀:

static class MyNamespaceContext implements NamespaceContext {

  private Map<String, String> ns;

  public MyNamespaceContext() {
    ns = new HashMap<String, String>();
    ns.put("xs", "http://www.w3.org/2001/XMLSchema");
    ns.put("soapenv", "http://schemas.xmlsoap.org/soap/envelope/");
    ns.put("pipeline", "http://pipeline_ws");
  }

  public String getNamespaceURI(String prefix) {
    return ns.get(prefix);
  }

  public Iterator<String> getPrefixes() {
    return ns.keySet().iterator();
  }

  public Iterator<String> getPrefixes(String namespaceURI) {
    final List<String> prefixes = new LinkedList<String>();
    if(namespaceURI != null) {
      for(Entry<String, String> entry: ns.entrySet()) {
        if(namespaceURI.equals(entry.getValue())) {
          prefixes.add(entry.getKey());
        }
      }
    }
    return prefixes.iterator();
  }

  public Map<String, String> getPrefixMapping() {
    return ns;
  }

  @Override
  public String getPrefix(String namespaceURI) {
    if(namespaceURI != null) {
      for(Entry<String, String> entry: ns.entrySet()) {
        if(namespaceURI.equals(entry.getValue())) {
          return entry.getKey();
        }
      }
    }
    return null;
  }    
}

第一个XML版本的输出是:

<fr><Result>
   <ListPartner>
        <operator>
            <country_code></country_code>
            <currency_code></currency_code>
            <operator_code></operator_code>

    </operator>
 </ListPartner>
</Result></fr>

第二个:

<fr>
<Result>
<ListPartner>
<operator>
<country_code></country_code>
<currency_code></currency_code>
<operator_code></operator_code>   
</operator>
</ListPartner>
</Result>
</fr>