#r #web-scraping #rvest
Вопрос:
Мы изо всех сил пытаемся захватить главный стол по этой ссылке на фанграфы. С помощью rvest
:
url = 'https://www.fangraphs.com/leaders/splits-leaderboards?splitArr=1amp;splitArrPitch=amp;position=Bamp;autoPt=falseamp;splitTeams=falseamp;statType=teamamp;statgroup=2amp;startDate=2021-07-07amp;endDate=2021-07-21amp;players=amp;filter=amp;groupBy=seasonamp;sort=9,1'
table_nodes = url %>% read_html() %>% html_nodes('table')
table_nodes
table_nodes
{xml_nodeset (7)}
[1] <table class="menu-standings-table"><tbody><tr>n<td>rn <div class="menu-sub-header">AL East</div>rn ...
[2] <table class="menu-team-table">n<tr>n<td>rn <div class="menu-sub-header">AL East</div>rn ...
[3] <table class="menu-team-table">n<tr>n<td>rn <div class="menu-sub-header">AL East</div>rn ...
[4] <table>n<tr>n<td><a href="http://www.fangraphs.com/blogs/top-45-prospects-baltimore-orioles">BAL</a></td>n<td><a href="http://www.fangraphs.com/blogs/top-34-prospects ...
[5] <table>n<tr>n<td><a href="http://www.fangraphs.com/blogs/top-30-prospects-atlanta-braves">ATL</a></td>n<td><a href="http://www.fangraphs.com/blogs/top-49-prospects-ch ...
[6] <table>n<tr>n<td><a href="http://www.fangraphs.com/blogs/top-40-prospects-baltimore-orioles">BAL</a></td>n<td><a href="http://www.fangraphs.com/blogs/top-38-prospects ...
[7] <table>n<tr>n<td><a href="http://www.fangraphs.com/blogs/top-27-prospects-atlanta-braves">ATL</a></td>n<td><a href="http://www.fangraphs.com/blogs/top-41-prospects-ch ...
Ни одна из этих 7 таблиц не является основной таблицей по URL-адресу со всей различной статистикой команды. url %>% read_html() %>% html_nodes('div.table-scroll')
возвращает пустой набор узлов и div.table-scroll
является div-оболочкой, в которой находится основная таблица.
Редактировать: Я предполагаю, что это сетевой запрос, но все еще не уверен, как получить вызов API из этого. Как увидеть полный вызов API для этого?
Комментарии:
1. Похоже, что эта таблица заполняется javascript (с отдельным запросом) после загрузки страницы. Я мало что сделал с
rvest
ним , но я подозреваю, что он, вероятно, не обрабатывает динамический контент.2. Похоже, что это действительно так. Я копаюсь в инструментах разработчика Chrome > Сеть >> XHR, пытаясь понять, могу ли я найти там что-нибудь, что можно почистить для этой таблицы, но не могу найти, откуда берутся данные для таблицы.
3. Я не вижу таблицы в источнике страницы. ps: в
Export Data
правом верхнем углу таблицы есть кнопка.4. да, кнопка «Экспорт данных» удобна, однако мы ищем программный подход к захвату этой таблицы и проведению некоторого анализа в R. Мы пытаемся удалить ручные аспекты (есть и другие таблицы, которые нужно захватить).
Ответ №1:
Данные динамически извлекаются из вызова API. Переключитесь на httr, так как вам нужно сделать запрос на публикацию, который включает дату начала/окончания. Кроме того, переключитесь на бесконечность с точки зрения возврата как можно большего количества данных с минимальным количеством вызовов.
Вы хотите преобразовать приведенное ниже в некоторую форму пользовательской функции, которая принимает аргументы даты.
library(httr)
library(purrr)
headers = c(
'user-agent' = 'Mozilla/5.0',
'content-type' = 'application/json;charset=UTF-8'
)
data = '{"strPlayerId":"all","strSplitArr":[1],"strGroup":"season","strPosition":"B","strType":"2","strStartDate":"2021-07-07","strEndDate":"2021-07-21","strSplitTeams":false,"dctFilters":[],"strStatType":"team","strAutoPt":"false","arrPlayerId":[],"strSplitArrPitch":[]}'
r <- httr::POST(url = 'https://www.fangraphs.com/api/leaders/splits/splits-leaders', httr::add_headers(.headers=headers), body = data) %>% content()
df <- map_df(r$data, data.frame)
Комментарии:
1. Спасибо, это просто фантастика. Как вы узнали, что нужно обратиться именно с этой
POST
просьбой?2. Я использовал вкладку «Сеть браузера» (F12 Chrome) для мониторинга веб-трафика при нажатии клавиши F5 для обновления страницы. Затем я поискал разделенные лидеры в записанном действии и использовал предварительный ответ для проверки правильности запроса.
3. Кстати, вам не нужен заголовок реферера. На самом деле нужен только тип контента.
4. Хорошо, спасибо. Я отредактировал вопрос, чтобы быстро показать 2 скриншота. Я нашел сетевой запрос с
split-leaders
, но не уверен, как «использовать предварительный просмотр ответа для проверки правильности запроса».