Невозможно прочитать элемент узла и его значение из XML с помощью Java - PullRequest
0 голосов
/ 07 апреля 2019

Я не могу прочитать элемент XML и его значение, используя XPath и DOMParser. Клиент отправляет этот XML как запрос в моем приложении, и у меня нет никакого контроля, чтобы манипулировать кодом Клиента. Я хочу прочитать AccountID с помощью DOMParser.

<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope" xmlns="https://billpayment.weaut.com/">
  <soap:Body>
    <GetAccountBalanceByAccount xmlns="https://billpayment.weaut.com/">
      <CompanyName>AABC</CompanyName>
      <Language>ENG</Language>
      <AccountID>54698214</AccountID>
    </GetAccountBalanceByAccount>
  </soap:Body>
</soap:Envelope>

Вот как я пытаюсь проанализировать XML, чтобы получить узел AccountID и его содержимое.

@RequestMapping(value = "/", method = { RequestMethod.POST}, consumes = {"text/xml"}, produces = "text/xml")    
    public ResponseEntity messageStub(@RequestBody String requestString)
            throws ClientProtocolException, IOException {       
        try {           
            DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
            dbf.setNamespaceAware(true);
            DocumentBuilder db = dbf.newDocumentBuilder();          
            Document doc = db.parse(new InputSource(new StringReader(requestString)));          
            XPathFactory xPathFactory = XPathFactory.newInstance();
            XPath xpath = xPathFactory.newXPath();
            javax.xml.namespace.NamespaceContext ns = new javax.xml.namespace.NamespaceContext()
            {               
                    @Override
                    public String getNamespaceURI(String prefix) 
                    {
                        if ( "soap".equals( prefix ) )
                        {                           
                            return "http://www.w3.org/2003/05/soap-envelope";
                        }                                                                                                              
                        return javax.xml.XMLConstants.NULL_NS_URI;
                   }
                   @Override
                   public String getPrefix(String namespaceURI) 
                   {
                      return null;
                   }
                    @Override
                    public Iterator<?> getPrefixes(String namespaceURI) 
                    {
                        return null;
                    }
            };       
            xpath.setNamespaceContext(ns);
            String nodeName="", nodeContent="";         
            NodeList nodeList = null;
            //XML Path
            String chkXMLPath="/soap:Envelope/soap:Body/GetAccountBalanceByAccount/AccountID";

            XPathExpression expr = xpath.compile(chkXMLPath);      
            //evaluating each node set against the requested xml
            Object result = expr.evaluate(doc, XPathConstants.NODESET);
            nodeList = (NodeList) result;                   
            //Here I am getting 0 node
            System.out.println("Got " + nodeList.getLength() + " nodes");                               
            for (int i = 0; i < nodeList.getLength(); i++) 
            {                                               
                nodeName = nodeList.item(i).getNodeName();
                nodeContent = nodeList.item(i).getTextContent();                        
                System.out.println("\nCurrent Element :" + nodeName);
                System.out.println("\nCurrent Value :" + nodeContent);
                break;
            }                                                                   
        }
    }

Когда я тестирую этот метод после удаления пространства имен xmlns из обоих мест, я могу прочитать элемент и его содержимое. Подскажите, пожалуйста, как мне прочитать AccountID и его содержимое без изменения XML.

1 Ответ

0 голосов
/ 08 апреля 2019

Хотя я решил эту проблему, удалив пространство имен xmlns из XML.Я использую метод ниже, чтобы сделать это.Это дает мне правильный XML для работы.

public static String RemoveAllXmlNamespace(String xmlData)
     {
     //Regex for xmlNS
         String xmlnsRegex = "\\s+xmlns\\s*(:\\w)?\\s*=\\s*\\\"(?<url>[^\\\"]*)\\\"";
         Pattern p = Pattern.compile(xmlnsRegex);
         Matcher m = p.matcher(xmlData); //get a matcher object
         int count = 0;
         while(m.find())
         {                 
           String replaceString= xmlData.substring(m.start(), m.end());
           //Removing xmlNS from the XML String
           xmlData = xmlData.replace(replaceString, "");
           System.out.println("xmlData: "+xmlData);
           break;
         }
         return xmlData;
    }

Приведенный выше код, по моему мнению, является самым безопасным способом избавиться от нежелательного пространства имен.Этот метод дает мне следующий XML в выводе.

<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope">
  <soap:Body>
    <GetAccountBalanceByAccount>
      <CompanyName>AABC</CompanyName>
      <Language>ENG</Language>
      <AccountID>54698214</AccountID>
    </GetAccountBalanceByAccount>
  </soap:Body>
</soap:Envelope>
...