Загрузка...

Parsing and processing a web page in PHP: choosing the best library.

Thread in Backend created by Hangman666 Jun 26, 2016. 591 view

  1. Hangman666
    Hangman666 Topic starter Jun 26, 2016 Хранитель Идей 342 Mar 10, 2016
    Задача спарсить и обработать необходимую информацию со стороннего сайта встает перед веб-разработчиком довольно часто и по самым разнообразным причинам: таким образом можно заполнять свой проект контентом, динамически подгружать какую-то информацию и так далее.

    В таких случаях перед программистом встает вопрос: какую из десятков библиотек выбрать? В этой статье мы постарались рассмотреть самые популярные варианты и выбрать из них лучший.


    Регулярные выражения
    Даже не смотря на то, что «регулярки» — это первое, что приходит на ум, использовать их для настоящих проектов не стоит.

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

    Вместо «допиливания» своего регулярного выражения при каждом малейшем изменении кода рекомендуем использовать инструменты ниже — это и проще, и удобнее, и надежнее.

    XPath и DOM
    DOM и XPath не являются библиотеками в привычном смысле этого слова, это стандартные модули, которые встроены в PHP начиная с пятой версии. Именно отсутствие необходимости использовать сторонние решения делает их одними из лучших инструментов для парсинга HTML страниц.

    [IMG]

    На первый взгляд может показаться, что низкий порог входа — это не о них, некоторые места и вправду являются весьма сложными. Но это только на первый взгляд: стоит только немного разобраться с синтаксисом и базовыми принципами, как XPath тут же станет для вас инструментом для парсинга номер один.

    Вот, например, код с использованием DOM и XPath, который ищет в разметке все теги и модифицирует их атрибуты src:
    Code

    $dom = new DOMDocument;
    $dom->loadHTML($html);
    $images = $dom->getElementsByTagName('img');

    foreach ($images as $image) {
    $image->setAttribute('src', 'http://example.com/' . $image->getAttribute('src'));
    }
    $html = $dom->saveHTML();
    Тем не менее, данный вариант не лишен минусов — для парсинга используется движок, в первую очередь предназначенный для работы с XML, а XML и HTML хоть и являются очень похожими языками, но всё же различаются. Из этого вытекают специфические требования к разметке: например, все HTML теги должны быть закрыты.

    Simple HTML DOM
    Simple HTML DOM — PHP-библиотека, позволяющая парсить HTML-код с помощью удобных jQuery-подобных селекторов.

    Она лишена главного недостатка XPath — библиотека умеет работать даже с невалидным HTML-кодом, что значительно упрощает работу. Вы также забудете о проблемах с кодировкой: все преобразования выполняются автоматически.

    Как и JQuery, Simple HTML DOM умеет искать и фильтровать вложенные элементы, обращаться к их атрибутам и даже выбирать отдельные логические элементы кода, например, комментарии.

    В этом примере сначала подгружается, а потом модифицируется заранее заготовленный HTML-код: во второй строке происходит добавление атрибута class со значением bar первом попавшемуся элементу div, а в следующей строке мы заменяем текст элемента с id=”world” на foo.
    Code

    $html = str_get_html('<div id="hello">Hello</div><div id="world">World</div>');
    $html->find('div', 1)->class = 'bar';
    $html->find('div[id=world]', 0)->innertext = 'foo';
    echo $html;
    Несмотря на не самую высокую производительность, по сравнению с другими вариантами, Simple HTML DOM имеет самое большое русскоязычное комьюнити и наибольшую распространенность в рунете — для новичков это делает написание кода с её использованием значительно проще.


    phpQuery
    Как и Simple HTML DOM, phpQuery является PHP вариантом JQuery, но на этот раз более похожим на своего «старшего javascript-брата».

    Портировано почти всё, что есть в JS-фреймворке: поддержка селекторов, атрибутов, манипуляций, обхода, плагинов, событий (в том числе имитации кликов и т.д.) и даже AJAX. Использовать можно как через PHP, так и через командную строку в виде отдельного приложения.

    Более того, согласно нашим бенчмаркам, phpQuery оказался в 8 (!) раз быстрее Simple HTML DOM.

    Вот небольшой пример на phpQuery, в котором происходит обработка заранее выбранных элементов списка (li):
    Code

    foreach(pq('li') as $li) {
    // Можно вывести различные данные обычным текстом
    $tagName = $li->tagName;
    $childNodes = $li->childNodes;
    // А можно добавить обертку phpQuery (аналог $() в JQuery) и, например, добавить к элементу какой-то класс
    pq($li)->addClass('my-second-new-class');
    }
    Подробную документацию и больше примеров найдете на официальной странице в Google Code.


    htmlSQL
    htmlSQL — экспериментальная PHP библиотека, позволяющая манипулировать HTML-разметкой посредством SQL-подобных запросов.

    Простейший пример, извлекающий атрибуты href и title всех ссылок (элементы a) с классом list:
    Code
    SELECT href,title FROM a WHERE $class == "list"
    Как и с обычными mysql_ функциями, воспользовавшись методами fetch_array() или fetch_objects(), мы можем получить результат выполнения данного запроса в виде привычного ассоциативного массива или объекта.

    Стоит также упомянуть о высоком быстродействии htmlSQL: часто она справляется в несколько раз быстрее phpQuery или того же Simple HTML DOM.

    Тем не менее, для сложных задач вам может не хватить функциональности, а разработка библиотеки давно прекращена. Но даже несмотря на это, она всё ещё представляет интерес для веб-разработчиков: в ряде случаев значительно удобнее использовать язык SQL вместе CSS-селекторов. Особенно когда вы не знаете, что такое CSS-селекторы.


    Вывод
    В своем мини-исследовании мы пришли к выводу, что в большинстве случаев для парсинга лучше использовать библиотеку phpQuery: она быстрая, функциональная и современная.

    С другой стороны, для совсем простых задач логично было бы использовать стандартные модули PHP, такие как XPath, DOM или, на крайний случай, регулярные выражения.

    Что-то ещё?
    Для PHP существуют ещё десятки разнообразных библиотек и инструментов для парсинга, но в этой статье мы рассмотрели только самые интересные, функциональные и производительные.

    Подробнее о других способах парсинга средствами PHP можно прочитать в соответствующей теме на StackOverflow.

    Если вы не используете PHP, то можете ознакомится с кратким списком похожих инструментов для других языков программирования:

    C++: htmlcxx, libxml++;

    Python: lxml, BeautifulSoup, html5lib;

    Java: JSOUP, TagSoup;

    Ruby: Nokogiri, Oga, Rubyful Soup;

    Perl: HTML::TokeParser, HTML:: Parser, HTML::SimpleParse;

    .NET: Html Agility Pack;

    Swift: libxml 2, Hpple;

    Ассемблер: AsmXml.
     
Loading...
Top