简体   繁体   English

无法使用dom4j从xml字符串解析节点

[英]unable to parse a node from xml string with dom4j

I'm parsing a xml string with dom4j and I'm using xpath to select some element from it, the code is : 我正在使用dom4j解析xml字符串,并且正在使用xpath从中选择一些元素,代码是:

    String test = "<?xml version=\"1.0\" encoding=\"UTF-8\"?><epp xmlns=\"urn:ietf:params:xml:ns:epp-1.0\"><response><result code=\"1000\"><msg lang=\"en-US\">Command completed successfully</msg></result><trID><clTRID>87285586-99412370</clTRID><svTRID>52639BB8-1-ARNES</svTRID></trID></response></epp>";
    SAXReader reader = new SAXReader();
    reader.setIncludeExternalDTDDeclarations(false);
    reader.setIncludeInternalDTDDeclarations(false);
    reader.setValidation(false);
    Document xmlDoc;
    try {
        xmlDoc = reader.read(new StringReader(test));
        xmlDoc.getRootElement();
        Node nodeStatus = xmlDoc.selectSingleNode("//epp/response/result");

        System.out.print(nodeStatus.getText());
    } catch (DocumentException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

I always get null for the nodeStatus variable. 我总是为nodeStatus变量获取null。 I actualy nead to read the code from the result noad from the xml 我实际上需要从xml的结果noad中读取代码

<result code="1000">

This is the XML that I am reading from the String test : 这是我从String test读取的XML:

<?xml version="1.0" encoding="UTF-8"?>
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
    <response>
        <result code="1000">
            <msg lang="en-US">Command completed successfully</msg>
        </result>
        <trID>
            <clTRID>87285586-99412370</clTRID>
            <svTRID>52639BB8-1-ARNES</svTRID>
        </trID>
    </response>
</epp>

Any hints? 有什么提示吗?

Your XML has a namespace. 您的XML具有名称空间。 DOM4J returns null because it won't find your nodes. DOM4J返回null,因为它找不到您的节点。

To make it work, you first have to register the namespaces you are using. 要使其正常工作,首先必须注册正在使用的名称空间。 You will need a prefix. 您将需要一个前缀。 Any one. 任何人。 And you will have to use that prefix in your XPath. 并且您将必须在XPath中使用该前缀。

You could use tns for "target namespace". 您可以将tns用作“目标名称空间”。 Then you have to create a xpath object with it like this: 然后,您必须像这样创建一个xpath对象:

XPath xpath = new DefaultXPath("/tns:epp/tns:response/tns:result");

To register the namespaces you will need to create a Map , add the namespace with the prefix you used in the xpath expression, and pass it to the setNamespaceURIs() method. 要注册名称空间,您将需要创建一个Map ,添加名称空间以及在xpath表达式中使用的前缀,然后将其传递给setNamespaceURIs()方法。

namespaces.put("tns", "urn:ietf:params:xml:ns:epp-1.0");
xpath.setNamespaceURIs(namespaces);

Now you can call selectSingleNode , but you will call it on your XPath object passing the document as the argument: 现在,您可以调用selectSingleNode ,但是您将在XPath对象上调用它,并将文档作为参数传递:

Node nodeStatus = xpath.selectSingleNode(xmlDoc);

From there you can extract the data you need. 从那里您可以提取所需的数据。 getText() won't give you the data you want. getText()不会为您提供所需的数据。 If you want the contents of the result node as XML, you can use: 如果希望结果节点的内容为XML,则可以使用:

nodeStatus.asXML()

Edit : to retrieve just the code, change your XPath to: 编辑 :仅检索代码,将XPath更改为:

/tns:epp/tns:response/tns:result/@code

And retrieve the result with 并用

nodeStatus.getText();

I replaced the double slash // (which means descendant-or-self) with / since the expression contains the full path and / is more efficient. 我取代双斜线//与(这意味着后代或自身) /因为表达式包含完整的路径和/更有效。 But if you only have one result node in your whole file, you can use: 但是,如果整个文件中只有一个result节点,则可以使用:

//result/@code

to extract the data. 提取数据。 It will match all descendants. 它将匹配所有后代。 If there is more than one result , it will return a node-set. 如果result不止一个,它将返回一个节点集。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM