Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

xmlns declaration broke my xPath filter

Tags:

xml

matlab

xpath

I have realized a really stupid xPath filter in MatLab:

% Construct the DOM.
docNode = xmlread('C:\Users\MATLAB\test.gpx');

% get the xpath mechanism into the workspace
import javax.xml.xpath.*
factory = XPathFactory.newInstance;
xpath = factory.newXPath;

% compile and evaluate the XPath Expression
expression = xpath.compile('gpx/AddressBook/Entry/PhoneNumber');
phoneNumberNode = expression.evaluate(docNode, XPathConstants.NODE);
phoneNumber = phoneNumberNode.getTextContent

With this XML (specifically a .gpx file) it works:

<?xml version='1.0' encoding='ISO-8859-1' standalone='yes' ?>
<gpx version='1.1' creator='TTTracklog V.1.13'>
    <AddressBook>
       <Entry>
          <Name>Friendly J. Mathworker</Name>
          <PhoneNumber>(508) 647-7000</PhoneNumber>
          <Address hasZip="no" type="work">3 Apple Hill Dr, Natick MA</Address>
       </Entry>
    </AddressBook>
</gpx>

and text (508) 647-7000 is returned. Simply adding xmlns attribute to gpx node in this way:

<?xml version='1.0' encoding='ISO-8859-1' standalone='yes' ?>
<gpx version='1.1' creator='TTTracklog V.1.13'  xmlns='http://www.topografix.com/GPX/1/1'>
    <AddressBook>
       <Entry>
          <Name>Friendly J. Mathworker</Name>
          <PhoneNumber>(508) 647-7000</PhoneNumber>
          <Address hasZip="no" type="work">3 Apple Hill Dr, Natick MA</Address>
       </Entry>
    </AddressBook>
</gpx>

gave me error, and matlab report:

??? Attempt to reference field of non-structure array.

Error in ==> test at 12 phoneNumber = phoneNumberNode.getTextContent

Why? How can I avoid that error?

like image 600
BAD_SEED Avatar asked Oct 14 '11 15:10

BAD_SEED


People also ask

What is an XPath filter?

XPath expressions are used to select nodes within XML trees. XPath expressions can be used for complex problems if there is a possibility to filter the current expressions once again in order to define more exact target volumes of nodes. For this application, XPath expressions may contain so-called predicates.

Does XPath require namespace?

XPath queries are aware of namespaces in an XML document and can use namespace prefixes to qualify element and attribute names. Qualifying element and attribute names with a namespace prefix limits the nodes returned by an XPath query to only those nodes that belong to a specific namespace.

What is namespace in XPath?

Namespaces provide a way of qualifying names that are used for elements, attributes, data types, and functions in XPath. Names in XPath are called QNames (qualified names) and conform to the syntax that is defined in the W3C Recommendation Namespaces in XML .


1 Answers

In case you cannot register the default namespace with an associated prefix, use:

*[name()= 'gpx']
    /*[name()='AddressBook']
       /*[name()='Entry']
          /*[name() = 'PhoneNumber']

instead of:

gpx/AddressBook/Entry/PhoneNumber

Here is a complete, XSLT-based, verification:

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>

 <xsl:template match="/">
     <xsl:copy-of select=
     "*[name()= 'gpx']
    /*[name()='AddressBook']
       /*[name()='Entry']
          /*[name() = 'PhoneNumber']
   "/>
 </xsl:template>
</xsl:stylesheet>

when this transformation is applied on the provided XML document:

<?xml version='1.0' encoding='ISO-8859-1' standalone='yes' ?>
<gpx version='1.1' creator='TTTracklog V.1.13'  xmlns='http://www.topografix.com/GPX/1/1'>
    <AddressBook>
       <Entry>
          <Name>Friendly J. Mathworker</Name>
          <PhoneNumber>(508) 647-7000</PhoneNumber>
          <Address hasZip="no" type="work">3 Apple Hill Dr, Natick MA</Address>
       </Entry>
    </AddressBook>
</gpx>

the wanted element is selected and copied to the output:

<PhoneNumber xmlns="http://www.topografix.com/GPX/1/1">(508) 647-7000</PhoneNumber>
like image 149
Dimitre Novatchev Avatar answered Sep 30 '22 18:09

Dimitre Novatchev