Как вы анализируете и обрабатываете HTML / XML в PHP? - PullRequest
2034 голосов
/ 26 августа 2010

Как можно проанализировать HTML / XML и извлечь из него информацию?

Ответы [ 30 ]

38 голосов
/ 07 ноября 2012

Я рекомендую PHP Простой HTML DOM Parser .

Он действительно имеет хорошие функции, такие как:

foreach($html->find('img') as $element)
       echo $element->src . '<br>';
36 голосов
/ 14 апреля 2011

Звучит как хорошее описание задачи технологии W3C XPath . Легко выражать запросы типа «вернуть все href атрибуты в img тегах, вложенных в <foo><bar><baz> elements» Не будучи фанатом PHP, я не могу сказать вам, в какой форме XPath может быть доступен. Если вы можете вызвать внешнюю программу для обработки HTML-файла, вы сможете использовать версию XPath для командной строки. Для быстрого вступления см. http://en.wikipedia.org/wiki/XPath.

29 голосов
/ 07 сентября 2010

Сторонние альтернативы SimpleHtmlDom, использующие DOM вместо анализа строк: phpQuery , Zend_Dom , QueryPath и FluentDom .

24 голосов
/ 05 января 2012

Да, вы можете использовать simple_html_dom для этой цели. Тем не менее, я довольно много работал с simple_html_dom, особенно для удаления из Интернета, и обнаружил, что он слишком уязвим. Это делает основную работу, но я не буду рекомендовать это так или иначе.

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

Пожалуйста, проверьте эту ссылку: Соскоб-сайты-с-curl

23 голосов
/ 15 апреля 2012

QueryPath - это хорошо, но будьте осторожны с «состоянием отслеживания», если вы не понимаете, что это значит, это может означать, что вы тратите много времени на отладку, пытаясь выяснить, что произошло и почему код не работает.

Это означает, что каждый вызов в наборе результатов изменяет набор результатов в объекте, он не является цепным, как в jquery, где каждая ссылка является новым набором, у вас есть один набор, который является результатом вашего запроса, и каждый вызов функции изменяет этот единственный набор.

Чтобы получить jquery-подобное поведение, вам нужно выполнить ветвление, прежде чем выполнять операцию, подобную фильтрующему / изменяющему, что означает, что он будет более точно отражать то, что происходит в jquery.

$results = qp("div p");
$forename = $results->find("input[name='forename']");

$results теперь содержит результирующий набор для input[name='forename'] НЕ исходный запрос "div p" Это меня сильно смутило, я обнаружил, что QueryPath отслеживает фильтры, находит и все, что модифицирует ваши результаты и сохраняет их в объекте. вам нужно сделать это вместо

$forename = $results->branch()->find("input[name='forname']")

тогда $results не будет изменен, и вы сможете снова и снова использовать набор результатов, возможно, кто-то, обладающий гораздо большими знаниями, может немного прояснить это, но в основном это похоже на то, что я нашел.

19 голосов
/ 18 декабря 2014

Advanced Html Dom представляет собой простую замену HTML DOM , которая предлагает тот же интерфейс, но на основе DOM, что означает отсутствие проблем с памятью.

Он также имеет полную поддержку CSS, включая jQuery расширения.

18 голосов
/ 08 июля 2013

Для HTML5 , html5 lib уже давно отменен.Единственная библиотека HTML5, которую я могу найти с недавними записями об обновлениях и обслуживании, это html5-php , которая была только что переведена в бета-версию 1.0 чуть более недели назад.

17 голосов
/ 09 июля 2015

Я создал библиотеку с именем PHPPowertools / DOM-Query , которая позволяет сканировать документы HTML5 и XML так же, как вы делаете это с jQuery.

Под капотом он использует symfony / DomCrawler для преобразования селекторов CSS в XPath селекторы. Он всегда использует один и тот же DomDocument, даже при передаче одного объекта другому, чтобы обеспечить достойную производительность.


Пример использования:

namespace PowerTools;

// Get file content
$htmlcode = file_get_contents('https://github.com');

// Define your DOMCrawler based on file string
$H = new DOM_Query($htmlcode);

// Define your DOMCrawler based on an existing DOM_Query instance
$H = new DOM_Query($H->select('body'));

// Passing a string (CSS selector)
$s = $H->select('div.foo');

// Passing an element object (DOM Element)
$s = $H->select($documentBody);

// Passing a DOM Query object
$s = $H->select( $H->select('p + p'));

// Select the body tag
$body = $H->select('body');

// Combine different classes as one selector to get all site blocks
$siteblocks = $body->select('.site-header, .masthead, .site-body, .site-footer');

// Nest your methods just like you would with jQuery
$siteblocks->select('button')->add('span')->addClass('icon icon-printer');

// Use a lambda function to set the text of all site blocks
$siteblocks->text(function( $i, $val) {
    return $i . " - " . $val->attr('class');
});

// Append the following HTML to all site blocks
$siteblocks->append('<div class="site-center"></div>');

// Use a descendant selector to select the site's footer
$sitefooter = $body->select('.site-footer > .site-center');

// Set some attributes for the site's footer
$sitefooter->attr(array('id' => 'aweeesome', 'data-val' => 'see'));

// Use a lambda function to set the attributes of all site blocks
$siteblocks->attr('data-val', function( $i, $val) {
    return $i . " - " . $val->attr('class') . " - photo by Kelly Clark";
});

// Select the parent of the site's footer
$sitefooterparent = $sitefooter->parent();

// Remove the class of all i-tags within the site's footer's parent
$sitefooterparent->select('i')->removeAttr('class');

// Wrap the site's footer within two nex selectors
$sitefooter->wrap('<section><div class="footer-wrapper"></div></section>');

[...]

Поддерживаемые методы:


  1. Переименовано в 'select' по понятным причинам
  2. Переименовано в 'void', поскольку в PHP зарезервированное слово 'empty'

ПРИМЕЧАНИЕ:

Библиотека также включает собственный автозагрузчик нулевой конфигурации для PSR-0-совместимых библиотек. Приведенный пример должен работать из коробки без какой-либо дополнительной настройки. Кроме того, вы можете использовать его с композитором.

17 голосов
/ 12 мая 2013

Я написал анализатор XML общего назначения, который может легко обрабатывать файлы GB. Он основан на XMLReader и очень прост в использовании:

$source = new XmlExtractor("path/to/tag", "/path/to/file.xml");
foreach ($source as $tag) {
    echo $tag->field1;
    echo $tag->field2->subfield1;
}

Вот репозиторий github: XmlExtractor

15 голосов
/ 16 ноября 2008

Вы можете попробовать использовать что-то вроде HTML Tidy для очистки любого "сломанного" HTML и преобразования HTML в XHTML, который затем можно проанализировать с помощью анализатора XML.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...