2015-02-24 3 views
1

У меня есть XML, как это:SimpleXML xpath для элемента с определенным значением атрибута?

<item> 
    <custom-attributes> 
     <custom-attribute attribute-id="taco">false</custom-attribute> 
     <custom-attribute attribute-id="htmlContent" xml:lang="en-US">testValue</custom-attribute> 
     <custom-attribute attribute-id="htmlContent" xml:lang="default">testing123</custom-attribute> 
    </custom-attribute> 
</item> 

Как использовать XPath, чтобы найти custom-attribute элемент, чем имеет атрибут-идентификатор taco?

Как использовать xpath для поиска custom-attribute элементов (-ов), чем имеют атрибуты-идентификаторы от htmlContent? В этом случае 2. Также на них есть пространства имен. Я не уверен, что это важно или нет.

Я пытался что-то вроде этого:

var_dump($xml->xpath("custom-attribute[@attribute-id='taco']")); 

Но это не работает. Я могу перебирать элементы custom-attribute и искать то, что мне нужно, но было бы намного проще просто выбрать его через xpath.

Что мне здесь не хватает?

ответ

4

Добавить двойной слэш в начале вашего XPath:

$source = <<<X 
<item> 
    <custom-attributes> 
     <custom-attribute attribute-id="taco">false</custom-attribute> 
     <custom-attribute attribute-id="htmlContent" xml:lang="en-US">testValue</custom-attribute> 
     <custom-attribute attribute-id="htmlContent" xml:lang="default">testing123</custom-attribute> 
    </custom-attributes> 
</item> 
X; 

$xml = new SimpleXMLElement($source); 

$taco    = $xml->xpath("//custom-attribute[@attribute-id='taco']")[0]; 
$htmlContentArray = $xml->xpath("//custom-attribute[@attribute-id='htmlContent']"); 

echo "taco  : ", $taco, PHP_EOL; 
echo "htmlContent: ", implode(', ', $htmlContentArray), PHP_EOL; 

Выход:

taco  : false 
htmlContent: testValue, testing123 

Update

Для вашего вопроса в комментариях по поводу поиска в качестве item узла ; вы можете использовать .//, чтобы начать поиск с текущего узла.

// Find an item, then do an xpath on the result of that 
// to find the custom attribute element. 
// <items> tag added as <item> would otherwise be the root element, 
// which would make the example quite pointless. 
$source = <<<X 
<items> 
    <item> 
     <custom-attributes> 
      <custom-attribute attribute-id="taco">false</custom-attribute> 
      <custom-attribute attribute-id="htmlContent" xml:lang="en-US">testValue</custom-attribute> 
      <custom-attribute attribute-id="htmlContent" xml:lang="default">testing123</custom-attribute> 
     </custom-attributes> 
    </item> 
    <item> 
     <custom-attributes> 
      <custom-attribute attribute-id="taco">true</custom-attribute> 
      <custom-attribute attribute-id="htmlContent" xml:lang="en-US">item 2 testValue</custom-attribute> 
      <custom-attribute attribute-id="htmlContent" xml:lang="default">item 2 testing456</custom-attribute> 
      </custom-attributes> 
    </item> 
</items> 
X; 

$xml = new SimpleXMLElement($source); 

$item    = $xml->item[1]; // Get second item 
$taco    = $item->xpath(".//custom-attribute[@attribute-id='taco']"); 
$htmlContentArray = $item->xpath(".//custom-attribute[@attribute-id='htmlContent']"); 

echo "taco from second item: ", $taco[0], PHP_EOL; 
echo "html from second item: ", implode(', ', $htmlContentArray), PHP_EOL; 

Выход:

taco from second item: true 
html from second item: item 2 testValue, item 2 testing456 
+0

Так XPath возвращает массив, а не SimpleXMLElement? –

+0

Фактически выражения XPath возвращают список узлов или скаляр в зависимости от выражения, SimpleXML преобразует его в массив объектов SimpleXMLElement. – ThW

+0

Хммм. Можно ли использовать xpath для поиска «элемента», а затем выполнить xpath в результате этого, чтобы найти элемент пользовательского атрибута? Возможно, я немного упростил свой XML в моем вопросе. –

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