Веб-скрапинг с Puppeteer: практическое руководство

Puppeteer — один из самых популярных инструментов для автоматизации браузера на JavaScript. Разработчики используют его, чтобы управлять настоящим браузером из кода, без ручных кликов по страницам.
Та же самая возможность делает Puppeteer полезным для веб-скрейпинг. Многие современные сайты подгружают контент через JavaScript, и скраперу нужно видеть страницу так, как её видит браузер, а не только исходный HTML, который сервер отдаёт в первом ответе.
В этом руководстве объясняется, что такое Puppeteer, как он работает и как собрать на нём простой скрапер. Также разбираются практические проблемы, которые возникают, когда проект по скрапингу выходит за рамки одной тестовой страницы.
Что такое Puppeteer?

Puppeteer — это JavaScript-библиотека, которую поддерживает команда Chrome. Она даёт разработчикам высокоуровневый API для управления браузером из кода.
Puppeteer обычно используется вместе с Node.js. Скрипт на Puppeteer может открыть браузер, зайти на страницу, взаимодействовать с ней и считать её содержимое — и всё это без участия мыши и клавиатуры.
По умолчанию Puppeteer работает в headless-режиме. A безголовый браузер — это настоящий браузер, работающий без видимого окна. Это делает его эффективным для автоматизации, поскольку интерфейс не нужно отрисовывать.
Puppeteer может управлять Chrome и Chromium, а также поддерживает Firefox. Он взаимодействует с браузером через Chrome DevTools Protocol или WebDriver BiDi, в зависимости от конфигурации.
Puppeteer создан не только для скрапинга. Его также часто используют для:
- Автоматизированного тестирования веб-приложений
- Создания скриншотов страниц
- Генерации PDF из веб-страниц
- Мониторинга производительности страниц
- Общих задач автоматизации браузера
Веб-скрапинг — это лишь один из практических способов, которыми разработчики применяют управление браузером в Puppeteer.
Зачем использовать Puppeteer для веб-скрапинга?
Чтобы понять, чем полезен Puppeteer, стоит сравнить два разных подхода к скрапингу.
Традиционный HTTP-скрапинг:
Запрос → HTML → извлечение данных
Простой скрапер отправляет HTTP-запрос на URL и читает возвращённый HTML. Это хорошо работает для простых статических страниц.
Браузерный скрапинг с Puppeteer:
Открыть браузер → загрузить страницу → выполнить JavaScript → отрисовать контент → извлечь данные
Puppeteer открывает настоящий браузер, загружает страницу и позволяет JavaScript страницы отработать до того, как будут извлечены какие-либо данные. Это важно, потому что всё больше сайтов формируют свой контент динамически, уже после первичной загрузки страницы.
Веб-скрапинг с Puppeteer оказывается полезен когда страница полагается на JavaScript для отображения своего контента. Типичные примеры:
- Списки товаров, которые подгружаются после вызова API
- Фильтры и результаты поиска, которые обновляются без полной перезагрузки страницы
- Элементы пагинации, построенные на JavaScript
- Ленты с бесконечной прокруткой
- Интерактивные дашборды или приложения
- Контент, который появляется только после действия пользователя
Обычный HTTP-запрос увидел бы только исходный HTML страницы. Он пропустил бы всё, что браузер генерирует после этого. Именно поэтому веб-скрапинг страниц, отрисовываемых через JavaScript, обычно требует настоящего браузерного окружения, и именно поэтому Puppeteer часто выбирают для такого скрапинга на Node.js.
Как установить Puppeteer
Puppeteer устанавливается через npm, менеджер пакетов, который поставляется вместе с Node.js. Если Node.js уже настроен на вашей машине, установка Puppeteer занимает одну команду.
Эта команда добавляет Puppeteer в ваш проект и загружает совместимую версию Chrome, которой он будет управлять. Именно этот встроенный браузер Puppeteer запускает по умолчанию, поэтому для типовой настройки отдельная установка браузера не требуется.
Если вам нужен только API без встроенного браузера, puppeteer-core — более лёгкая альтернатива. Он предполагает, что вы подключаетесь к браузеру, которым управляете сами, а это скорее продвинутый сценарий использования.
Для повседневных проектов по скрапингу обычный puppeteer пакет — более простая отправная точка.
Как спарсить сайт с помощью Puppeteer
Лучший способ разобраться в скрапинге с Puppeteer это рассмотреть небольшой, но законченный пример. Он открывает страницу, ждёт её загрузки, считывает с неё текст и выводит результат.
Вот что делает каждая часть:
- puppeteer.launch() запускает новый экземпляр браузера. Это тот браузер , которым управляет ваш скрипт.
- browser.newPage() открывает новую вкладку внутри этого браузера. Это та страница , с которой будет работать ваш скрипт.
- page.goto() выполняет переход по URL. Параметр waitUntil указывает Puppeteer, как определить, что страница готова, прежде чем продолжить.
- page.$$eval() выбирает группу элементов на странице по CSS-селектору, а затем выполняет для них функцию внутри браузера. В этом примере он собирает названия всех книг на странице.
- browser.close() закрывает браузер после завершения работы скрипта. Если пропустить этот шаг вдлительном проекте, процессы браузера могут остаться работать в фоне.
Этот же шаблон — запустить, открыть страницу, дождаться, выбрать, извлечь, закрыть — лежит в основе большинства скраперов на Puppeteer. Более сложные проекты дополняют его дополнительными шагами для навигации, ожидания и обработки ошибок.
Скрапинг динамических сайтов с помощью Puppeteer
Статический парсинг HTML перестаёт работать, когда сайт строит своё содержимое с помощью JavaScript. Сервер отдаёт практически пустую страницу, а реальный контент добавляется позже скриптами, которые выполняются в браузере.
Именно для такой ситуации и создан Puppeteer. Поскольку он управляет полноценным браузером, JavaScript выполняется как обычно, а страница считывается уже тогда, когда контент действительно существует.
При парсинге динамических страниц регулярно возникает несколько типичных ситуаций.
Ожидание контента
Иногда элемента ещё нет на странице в тот момент, когда скрипт впервые его ищет. Puppeteer может дождаться появления конкретного селектора, прежде чем продолжить работу.
Это указывает Puppeteer сделать паузу, пока элемент, соответствующий .product-price не появится на странице, вместо того чтобы сразу завершиться ошибкой из-за того, что его пока не существует.
Клики по элементам
Часть контента появляется только после действия пользователя, например открытия вкладки или разворачивания раздела. Puppeteer может имитировать такой клик перед считыванием страницы.
Некоторые ленты подгружают новые элементы по мере прокрутки страницы. Парсер на Puppeteer может имитировать прокрутку, выполняя действие скролла внутри страницы а затем дожидаться появления новых элементов, прежде чем собирать их.
Пагинация
Многие сайты разбивают результаты на несколько страниц с помощью кнопок «далее» или номеров страниц. Puppeteer может проходить по ним в цикле, извлекая данные на каждой странице перед переходом к следующей.
Обычно эти приёмы комбинируются, а не используются по отдельности. Реальный парсер может дождаться загрузки страницы, нажать на фильтр, снова подождать и затем извлечь данные, и всё это в рамках одного скрипта.
Типичные проблемы при скрапинге с Puppeteer
Даже хорошо написанный парсер на Puppeteer сталкивается с предсказуемым набором проблем, как только выходит за пределы одной тестовой страницы.
Медленная загрузка страницы
Некоторые страницы загружаются дольше, чем ожидается, особенно при медленном соединении или на тяжёлых сайтах. Скрипт, который этого не учитывает, может завершиться по тайм-ауту или получить неполную страницу.
Реалистичные тайм-ауты и ожидание нужных элементов помогают этого избежать.
Динамический контент
Контент, который загружается асинхронно, не всегда доступен в тот момент, когда page.goto() завершает работу. Именно поэтому ожидание конкретных селекторов, а не фиксированной задержки, более надёжный подход.
Ограничения скорости
Слишком быстрая отправка запросов может активировать ограничение частоты обращений на сайте, из-за чего дальнейшие запросы замедляются или блокируются. Это часто происходит, когда скрапер переходит от нескольких тестовых запросов к более крупной задаче.
CAPTCHA и обнаружение ботов
Многие сайты используют системы, которые пытаются выявить автоматический трафик и показать CAPTCHA или заблокировать запрос. Они существуют потому, что сайт хочет ограничить автоматический доступ, и в любом проекте по скрапингу следует учитывать условия использования сайта.
Блокировки IP
Когда с одного IP-адреса за короткий промежуток времени поступает много запросов, некоторые сайты помечают или блокируют этот IP. Для небольших задач скрапинга это обычно не проблема.
Это становится реальным ограничением, когда проект предполагает частые запросы, большие объёмы данных илидлительные задачи, поскольку один IP начинает выглядеть необычно для целевого сайта.
Нужен ли прокси для Puppeteer?
Не каждому проекту на Puppeteer нужен прокси. Для небольшой задачи скрапинга часто достаточно прямого подключения.
Прокси становится актуальным, когда проект растёт в одном из этих направлений:
- Скрапинг в больших масштабах, с большим количеством запросов на протяжении времени
- Необходимость видеть сайт так, как его видят пользователи в конкретной стране или городе это
- Распределение трафика между несколькими IP-адресами вместо использования одного
- Обход ограничений частоты запросов по IP или блокировок
- Запуск задач скрапинга, которые продолжаются в течениедлительного времени
Без прокси каждый запрос из скрипта Puppeteer исходит с одного и того же IP-адреса. Прокси направляет этот трафик через другой IP или пул IP, поэтому запросы не выглядят так, будто все они приходят из одного источника.
Настройка прокси в Puppeteer включает несколько шагов конфигурации, в том числе аргументы запуска и аутентификацию. Поскольку эта настройка уже подробно разобрана в другом материале, в этом руководстве мы не будем ее повторять. Полное пошаговое описание конфигурации смотрите в руководстве по интеграции прокси с Puppeteer.
Какой тип прокси лучше всего подходит для скрапинга с Puppeteer?
Разные типы прокси подходят для разных задач скрапинга.
Резидентские прокси используют IP, связанные с реальными интернет-провайдерами. Они полезны для широкого географического охвата и крупных задач скрапинга. Ротационные резидентные прокси могут менять IP от запроса к запросу.
Мобильные прокси используют IP из сетей мобильных операторов. Они могут быть полезны, когда IP мобильных сетей лучше подходят для целевого сайта.
ISP прокси предлагают стабильные IP, зарегистрированные на интернет-провайдеров. Они хорошо подходят, когда скраперу нужен постоянный IP и более длительные сессии.
Лучший вариант зависит от сайта, масштаба скрапинга и от того, нужны ли вам ротационные или стабильные IP.
Использование прокси NodeMaven с Puppeteer
Как только скрапер на Puppeteer начинает отправлять большое количество запросов, опора на один IP-адрес становится реальным ограничением.
NodeMaven предоставляет ротационные резидентные прокси построенные на большом пуле IP с таргетингом по стране, городу и ZIP, а также с управлением сессиями, которое позволяет скрипту менять IP автоматически или сохранять липкую сессию на заданный период.
Также доступны мобильные прокси для сценариев, где предпочтительны IP мобильных сетей, например для скрапинга платформ, ориентированных на мобильные устройства, или для задач, где поведение мобильных IP важнее широкого охвата.

Полный процесс настройки, включая аргументы запуска и аутентификацию, смотрите в руководстве по интеграции прокси с Puppeteer.
Лучшие практики веб-скрапинга с Puppeteer
Несколько привычек делают скраперы на Puppeteer заметно надежнее на практике.
- Используйте реалистичную частоту запросов. Отправка запросов с максимальной скоростью повышает вероятность ограничений по частоте или блокировок. Распределение запросов во времени больше похоже на обычный трафик.
- Ожидайте появления контента вместо того, чтобы угадывать тайминг. Использование waitForSelector или аналогичные методы вместо фиксированной задержки, поскольку время загрузки бывает разным.
- Обрабатывайте таймауты и ошибки. Иногда страницы не загружаются. Если обернуть навигацию в блоки try и catch, одна неудачно загруженная страница не остановит весь скрипт.
- Эффективно переиспользуйте ресурсы браузера. Открывать и закрывать новый браузер для каждой страницы медленнее, чем по возможности использовать один браузер для нескольких страниц.
- Избегайте лишних загрузок страниц. Переходите только на те страницы, которые действительно нужны для сбора ваших данных.
- Используйте тип прокси-сессии, подходящий вашему рабочему процессу. Ротационные сессии подходят для скрапинга больших объёмов, а sticky-сессии - для задач, где нужно какое-то время оставаться на одном IP.
- Храните собранные данные структурированно. Сохранение результатов в едином формате, например JSON или CSV, упрощает использование данных после завершения сбора.




