2014-01-15 9 views
0

Я получил XMLAndroid почему xPath.String возвращает пустую строку?

<FictionBook xmlns="http://www.gribuser.ru/xml/fictionbook/2.0" xmlns:l="http://www.w3.org/1999/xlink"> 
    <description> 
    <title-info> 
     <genre>love_contemporary</genre> 
     <author> 
     <first-name>Sylvain</first-name> 
     <last-name>Reynard</last-name> 
     </author> 
     <book-title>Gabriel's Inferno</book-title> 
     <annotation> 
     <p>Enigmatic and sexy, Professor Gabriel Emerson is a well respected Dante specialist by day, but by night he devotes himself to an uninhibited life of pleasure. He uses his notorious good looks and sophisticated charm to gratify his every whim, but is secretly tortured by his dark past and consumed by the profound belief that he is beyond all hope of redemption. When the sweet and innocent Julia Mitchell enrolls as his graduate student, his attraction and mysterious connection to her not only jeopardizes his career, but sends him on a journey in which his past and his present collide. An intriguing and sinful exploration of seduction, forbidden love and redemption, Gabriel's Inferno is a captivating and wildly passionate tale of one man's escape from his own personal hell as he tries to earn the impossible…forgiveness and love.</p> 
     </annotation> 
     <date/> 
     <coverpage> 
     <image l:href="#_0.jpg"/> 
     </coverpage> 
     <lang>en</lang> 
     <src-lang>en</src-lang> 
     <sequence name="Gabriel's Inferno" number="1"/> 
    </title-info> 
    <document-info> 
     <author> 
     <first-name/> 
     <last-name/> 
     </author> 
     <date/> 
     <id>2aec7273-a8a4-4edc-803a-820c4d76bc3f</id> 
     <version>1.0</version> 
    </document-info> 
    <publish-info> 
     <book-name>Gabriel's Inferno</book-name> 
     <year>2011</year> 
    </publish-info> 
    </description> 
</FictionBook> 

мое выражение, чтобы получить значение атрибута

string(//coverpage/image/@l:href) 

кодекса в андроида программе

XPathFactory factory = XPathFactory.newInstance(); 
XPath xpath = factory.newXPath(); 
String expression; 
String attrValue; 

expression = "string(//coverpage/image/@l:href)"; 
try { 
    attrValue = xpath.compile(expression).evaluate(obj, 
     XPathConstants.STRING).toString(); 
    System.out.println("VAL XML:"+attrValue); 

} catch (XPathExpressionException e) { 
    // TODO Auto-generated catch block 
    e.printStackTrace(); 
} 

Но на консоли я получаю только:

VAL XML: 

Почему? Что я делаю неправильно?

Прошу http://www.freeformatter.com/xpath-tester.html#ad-output для онлайн-тестирования - все работает нормально. Получить строку # _0.jpg

ответ

1

Ваша проблема в том, что узел, который вы пытаетесь поймать, использует пространство имен XML, и фабрика не знает об этом. Я вижу два решения для этого:

без определения пространства имен

избежать проблем с помощью local-name() игнорировать пространство имен в целом.

//*[local-name() = 'coverpage']/*[local-name() = 'image']/@*[local-name() = 'href'] 

(//coverpage/image/@*[local-name() = 'href'] может работать, а)

Определение в пространстве имен

Make XPathFactory осведомлены о различных пространствах имен, так что он знает, какой из них использовать.

import javax.xml.namespace.NamespaceContext; 
... 
xpath.setNamespaceContext(new MyNamespaceContext()); 
attrValue = xpath.compile(expression).evaluate(obj, 
        XPathConstants.STRING).toString(); 
... 
private static class MyNamespaceContext implements NamespaceContext { 

    public String getNamespaceURI(String prefix) { 
     if("l".equals(prefix)) { 
      return "http://www.w3.org/1999/xlink"; 
     } 
     return null; 
    } 

    public String getPrefix(String namespaceURI) { 
     return null; 
    } 

    public Iterator getPrefixes(String namespaceURI) { 
     return null; 
    } 

} 

(возможно дубликат: How to use XPath on xml docs having default namespace)

+0

Это работает, спасибо. Но я не могу понять, как написать xpath, чтобы получить значение атрибута без пространства имен? Я пытаюсь // * [local-name() = 'coverpage'] // * [local-name() = 'image']/@ l: href - не работает :( –

+0

Это потому, что вы должны использовать 'local- name() 'для атрибута' href', так как он имеет пространство имен, отличное от значения по умолчанию: что-то вроде '// * [local-name() = 'coverpage']/* [local-name() = 'image ']/@ * [local-name() =' href '] '(это также может работать // // coverpage/image/@ * [local-name() =' href ']'). Я обновлю ответ. – Robin

Смежные вопросы