Итак, проблема в том, что страница отображается с помощью javascript.Поэтому rvest
само по себе не будет работать.Один из самых простых способов исправить это - использовать безголовый веб-браузер.Мы можем использовать PhantomJS
.
Сначала загрузите соответствующую версию PhantomJS
и поместите исполняемый файл (при условии Windows) в свой рабочий каталог.То есть буквально phantomjs.exe
находится в рабочем каталоге скрипта R
.
Создайте файл scrape.js
:
// scrape.js
var webPage = require('webpage');
var page = webPage.create();
var fs = require('fs');
var path = 'page.html';
page.open('https://www.cenace.gob.mx/DocsMEM/OpeMdo/OfertaCompVent/OferVenta/MDA/Termicas/OfeVtaTermicaHor%20BCS%20MDA%20Hor%202018-12-26%20v2019%2002%2024_01%2000%2001.html', function (status) {
var content = page.content;
fs.write(path,content,'w');
phantom.exit();
});
Этот файл scrape.js
после запуска, создаст файл page.html
в вашем рабочем каталоге.Вернувшись в R
или RStudio
, вы можете сделать следующее:
library(tidyverse)
library(rvest)
# Run scrape.js with PhantomJS to create the file page.html
system("./phantomjs scrape.js")
# Now we should be in business as usual:
read_html('page.html') %>%
html_nodes("table#Tabc") %>%
html_table(header = TRUE) %>%
.[[1]] %>%
as_tibble()
# A tibble: 504 x 38
Codigo `Estatus asigna~ Hora `Limite de desp~ `Limite de desp~ `Costo de Opera~ `Bloque de Pote~ `Costo Incremen~ `Bloque de Pote~
<chr> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 BTY5W~ ECO 1 35 20 43212. 1.5 1762. 1.5
2 BTY5W~ ECO 2 35 20 43212. 1.5 1762. 1.5
3 BTY5W~ ECO 3 35 20 43212. 1.5 1762. 1.5
4 BTY5W~ ECO 4 35 20 43212. 1.5 1762. 1.5
5 BTY5W~ ECO 5 35 20 43212. 1.5 1762. 1.5
6 BTY5W~ ECO 6 35 20 43212. 1.5 1762. 1.5
7 BTY5W~ ECO 7 35 20 43212. 1.5 1762. 1.5
8 BTY5W~ ECO 8 35 20 43212. 1.5 1762. 1.5
9 BTY5W~ ECO 9 35 20 43212. 1.5 1762. 1.5
10 BTY5W~ ECO 10 35 20 43212. 1.5 1762. 1.5
# ... with 494 more rows, and 29 more variables: `Costo Incremental de generacion Bloque 02 ($/MWh)` <dbl>, `Bloque de Potencia 03 (MW)` <dbl>,
# `Costo Incremental de generacion Bloque 03 ($/MWh)` <dbl>, `Bloque de Potencia 04 (MW)` <dbl>, `Costo Incremental de generacion Bloque 04
# ($/MWh)` <dbl>, `Bloque de Potencia 05 (MW)` <dbl>, `Costo Incremental de generacion Bloque 05 ($/MWh)` <dbl>, `Bloque de Potencia 06
# (MW)` <dbl>, `Costo Incremental de generacion Bloque 06 ($/MWh)` <dbl>, `Bloque de Potencia 07 (MW)` <dbl>, `Costo Incremental de generacion
# Bloque 07 ($/MWh)` <dbl>, `Bloque de Potencia 08 (MW)` <dbl>, `Costo Incremental de generacion Bloque 08 ($/MWh)` <dbl>, `Bloque de Potencia
# 09 (MW)` <dbl>, `Costo Incremental de generacion Bloque 09 ($/MWh)` <dbl>, `Bloque de Potencia 10 (MW)` <dbl>, `Costo Incremental de
# generacion Bloque 10 ($/MWh)` <dbl>, `Bloque de Potencia 11 (MW)` <dbl>, `Costo Incremental de generacion Bloque 11 ($/MWh)` <dbl>, `Reserva
# rodante 10 min (MW)` <dbl>, `Costo Reserva rodante 10 min ($/MW)` <dbl>, `Reserva no rodante 10 min (MW)` <dbl>, `Costo Reserva no rodante 10
# min ($/MW)` <dbl>, `Reserva rodante suplementaria (MW)` <dbl>, `Costo Reserva rodante suplementaria ($/MW)` <dbl>, `Reserva no rodante
# suplementaria (MW)` <dbl>, `Costo Reserva no rodante suplementaria ($/MW)` <dbl>, `Reserva regulacion secundaria (MW)` <dbl>, `Costo Reserva
# regulacion secundaria ($/MW` <dbl>
Обновление масштаба до нескольких URL-адресов
Сначала измените файл scrape.js
, чтобы он принимал аргументы:
// scrape2.js
var webPage = require('webpage');
var page = webPage.create();
var system = require('system');
var args = system.args;
var fs = require('fs');
var path = args[2];
page.open(args[1], function (status) {
var content = page.content;
fs.write(path,content,'w');
phantom.exit();
});
Затем создайте списки для зацикливания / обхода / отображения (очевидно, это можно было бы очистить / абстрагировать, чтобы было проще поддерживать и было меньше необходимости печатать):
urls <- list(
'https://www.cenace.gob.mx/DocsMEM/OpeMdo/OfertaCompVent/OferVenta/MDA/Termicas/OfeVtaTermicaHor%20BCS%20MDA%20Hor%202018-12-26%20v2019%2002%2024_01%2000%2001.html',
'https://www.cenace.gob.mx/DocsMEM/OpeMdo/OfertaCompVent/OferVenta/MDA/Termicas/OfeVtaTermicaHor%20SIN%20MDA%20Hor%202018-12-29%20v2019%2002%2027_01%2000%2001.html',
'https://www.cenace.gob.mx/DocsMEM/OpeMdo/OfertaCompVent/OferVenta/MDA/Termicas/OfeVtaTermicaHor%20SIN%20MDA%20Hor%202018-12-29%20v2019%2002%2027_01%2000%2001.html'
)
paths <- list(
'page1.html',
'page2.html',
'page3.html'
)
args_list <- map2(urls, paths, paste)
# We are only using this function for the file creation side-effects,
# so we can use walk instead of map.
# This creates the files: page1.html, page2.html, and page3.html
walk(args_list, ~ system(paste("./phantomjs scrape2.js", .)))
На этом этапе вам, вероятно, захочется добавить информацию в функцию:
read_page <- function(page) {
read_html(page) %>%
html_nodes("table#Tabc") %>%
html_table(header = TRUE) %>%
.[[1]] %>%
as_tibble()
}
И оттуда вы можете повторно использовать список путей для отображения вашей новой функции:
paths %>%
map(~ read_page(.)) %>%
bind_rows()
# A tibble: 9,000 x 38
Codigo `Estatus asigna~ Hora `Limite de desp~ `Limite de desp~ `Costo de Opera~ `Bloque de Pote~ `Costo Incremen~ `Bloque de Pote~
<chr> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 BTY5W~ ECO 1 35 20 43212. 1.5 1762. 1.5
2 BTY5W~ ECO 2 35 20 43212. 1.5 1762. 1.5
3 BTY5W~ ECO 3 35 20 43212. 1.5 1762. 1.5
4 BTY5W~ ECO 4 35 20 43212. 1.5 1762. 1.5
5 BTY5W~ ECO 5 35 20 43212. 1.5 1762. 1.5
6 BTY5W~ ECO 6 35 20 43212. 1.5 1762. 1.5
7 BTY5W~ ECO 7 35 20 43212. 1.5 1762. 1.5
8 BTY5W~ ECO 8 35 20 43212. 1.5 1762. 1.5
9 BTY5W~ ECO 9 35 20 43212. 1.5 1762. 1.5
10 BTY5W~ ECO 10 35 20 43212. 1.5 1762. 1.5
# ... with 8,990 more rows, and 29 more variables: `Costo Incremental de generacion Bloque 02 ($/MWh)` <dbl>, `Bloque de Potencia 03 (MW)` <dbl>,
# `Costo Incremental de generacion Bloque 03 ($/MWh)` <dbl>, `Bloque de Potencia 04 (MW)` <dbl>, `Costo Incremental de generacion Bloque 04
# ($/MWh)` <dbl>, `Bloque de Potencia 05 (MW)` <dbl>, `Costo Incremental de generacion Bloque 05 ($/MWh)` <dbl>, `Bloque de Potencia 06
# (MW)` <dbl>, `Costo Incremental de generacion Bloque 06 ($/MWh)` <dbl>, `Bloque de Potencia 07 (MW)` <dbl>, `Costo Incremental de generacion
# Bloque 07 ($/MWh)` <dbl>, `Bloque de Potencia 08 (MW)` <dbl>, `Costo Incremental de generacion Bloque 08 ($/MWh)` <dbl>, `Bloque de Potencia
# 09 (MW)` <dbl>, `Costo Incremental de generacion Bloque 09 ($/MWh)` <dbl>, `Bloque de Potencia 10 (MW)` <dbl>, `Costo Incremental de
# generacion Bloque 10 ($/MWh)` <dbl>, `Bloque de Potencia 11 (MW)` <dbl>, `Costo Incremental de generacion Bloque 11 ($/MWh)` <dbl>, `Reserva
# rodante 10 min (MW)` <dbl>, `Costo Reserva rodante 10 min ($/MW)` <dbl>, `Reserva no rodante 10 min (MW)` <dbl>, `Costo Reserva no rodante 10
# min ($/MW)` <dbl>, `Reserva rodante suplementaria (MW)` <dbl>, `Costo Reserva rodante suplementaria ($/MW)` <dbl>, `Reserva no rodante
# suplementaria (MW)` <dbl>, `Costo Reserva no rodante suplementaria ($/MW)` <dbl>, `Reserva regulacion secundaria (MW)` <dbl>, `Costo Reserva
# regulacion secundaria ($/MW` <dbl>