Yes, don't use sed
on XML
. It's bad news.
I think your problem is actually a simple matter of quoting - you quote your xpath
in single quotes, and Elem
is also in single quotes.
I don't have a copy of xmllint
handy, but this works:
#!/usr/env/perl
use strict;
use warnings;
use XML::LibXML;
my $xml = XML::LibXML -> load_xml ( IO => \*DATA );
print $xml -> findnodes('//XML/*[local-name()="Elem"]');
__DATA__
<?xml version="1.0" encoding="UTF-8"?>
<XML>
<hhi:Elem xmlns:hhi="http://www.w3.org/TR/html4/" version="1.0" sn="101">
</hhi:Elem>
</XML>
That prints:
sn="101"
You don't need the XML
either, because //
denotes "anywhere in tree". So you could use:
//*[local-name()="Elem"]/@sn
/XML/*[local-name()="Elem"]/@sn
For the sake of completeness, with registering the namespace you could do it like this:
#!/usr/env/perl
use strict;
use warnings;
use XML::LibXML;
my $xml = XML::LibXML -> load_xml ( IO => \*DATA );
my $xpc = XML::LibXML::XPathContext -> new;
$xpc -> registerNs('x', 'http://www.w3.org/TR/html4/');
print $xpc -> findnodes('/XML/x:Elem/@sn', $xml);
__DATA__
<?xml version="1.0" encoding="UTF-8"?>
<XML>
<hhi:Elem xmlns:hhi="http://www.w3.org/TR/html4/" version="1.0" sn="101">
</hhi:Elem>
</XML>
Now, I know this doesn't directly help with xmllint
, aside from allowing testing of the xpath
you're using. But I think it likely that it's quotes tripping you up, not the xpath
.
Can I suggest you need:
xmllint --xpath '//*[local-name()="Elem"]/@sn' FILE_1.xml