Селен не отображает содержимое таблицы после нажатия кнопки

#python #selenium #csv #button #python-requests

#python #селен #csv #кнопка #python-запросы

Вопрос:

Я пытаюсь загрузить несколько CSV-файлов с приведенного ниже URL-адреса и надеюсь использовать для этого selenium или любой другой метод. URL требует заполнения формы, которая включает в себя выбор параметров из нескольких выпадающих списков. Затем необходимо нажать кнопку «изображение», чтобы появилась ссылка для скачивания. Если я запускаю драйвер selenium chrome из python и нажимаю на кнопку, ничего не появляется. Я также не могу определить URL-адрес файлов csv, чтобы их можно было загрузить с помощью «запросов» или «urllib».

Вот URL-адрес, с которого мне нужно загрузить: https://www1.nseindia.com/products/content/derivatives/equities/historical_fo.htm

Вот мой код до сих пор:

 from selenium import webdriver
from selenium.webdriver.support.ui import Select
from webdriver_manager.chrome import ChromeDriverManager

driver = webdriver.Chrome(ChromeDriverManager().install())

url = 'https://www1.nseindia.com/products/content/derivatives/equities/historical_fo.htm'
driver.get(url)
instr_type = Select(driver.find_element_by_id('instrumentType'))
symbol = Select(driver.find_element_by_id('symbol'))
opt_type = Select(driver.find_element_by_id('optionType'))
date_range = Select(driver.find_element_by_id('dateRange'))
button = driver.find_element_by_xpath("//input[@src='/common/images/btn-get-data.gif' and @type='image']")

instr_type.select_by_visible_text('Index Options')
symbol.select_by_visible_text('NIFTY 50')
opt_type.select_by_visible_text('CE')
date_range.select_by_visible_text('90 Days')
button.click()
 

И это то, что происходит в драйвере selenium —

Результат нажатия кнопки Selenium

Есть мысли о том, как загрузить csv-файлы по ссылке выше? Необязательно использовать selenium.

Комментарии:

1. разве вы не получаете сообщение об ошибке при его нажатии? Вы ждали / ждали ссылку для скачивания?

2. эта страница не работает для меня, когда я использую Selenium с Chrome или Firefox, но она работает в Chrome и Firefox без Selenium — у нее может быть некоторый конфликт с Selenium или она использует некоторую систему для блокировки сценариев, использующих Selenium

3. Я могу получить таблицу в виде HTML, используя requests , но я должен установить правильный user-agent — по крайней мере, короткий 'User-Agent': 'Mozilla/5.0' . Без user-agent кода зависает и никогда не заканчивается. Возможно, браузер с Selenium имеет аналогичную проблему. Но я не знаю, можно ли это исправить.

4. Я вижу, что он использует JavaScript для получения данных из этого HTML и генерации CSV, преобразованного в base64, и встраивания непосредственно в link. Так что, возможно, было бы быстрее и проще получить HTML с данными и очистить данные с BeautifulSoup помощью or lxml .

Ответ №1:

Я не знаю, как решить проблему, Selenium но теперь я знаю, как ее получить с requests помощью и BeautifulSoup

Эта страница отправляет ваши параметры из формы на эту страницу в виде значений непосредственно в этом URL (не как POST )

https://www1.nseindia.com/products/dynaContent/common/productsSymbolMapping.jsp

и сервер отправляет обратно HTML таблицу, а также все данные <div id="csvContentDiv"> .
В этом теге все данные в виде текста уже отформатированы для сохранения csv — его нужно только заменить : на n


Редактировать:

Иногда сервер выдает мне Status 405 Method Not Allowed , поэтому я добавил requests.Session() , чтобы получить файлы cookie, и, возможно, это будет работать лучше.


 import requests
from bs4 import BeautifulSoup

session = requests.Session()
session.headers.update({'User-Agent': 'Mozilla/5.0'})

# --- main page ---
url = 'https://www1.nseindia.com/products/content/derivatives/equities/historical_fo.htm'
r = session.get(url)
#print(r.status_code)

# --- table ---

url = 'https://www1.nseindia.com/products/dynaContent/common/productsSymbolMapping.jsp'

payload = {
    'instrumentType': 'OPTIDX',
    'symbol': 'NIFTY',
    'expiryDate': 'select',
    'optionType': 'CE',
    'strikePrice': '',
    'dateRange': '3month', 
    'fromDate': '',
    'toDate': '',
    'segmentLink': '9',
    'symbolCount':'',
}

r = session.get(url, params=payload)
#print(r.text)

soup = BeautifulSoup(r.text, 'html.parser')
data = soup.find('div', {'id': 'csvContentDiv'})
#print(data.text)
data = data.text.replace(':', 'n')

with open('output.csv', 'w') as fh:
    fh.write(data)

print(data)
 

Сервер не отправляет данные, если вы не используете real User-Agent — по крайней мере, short 'Mozilla/5.0'


Я нашел этот URL-адрес, используя DevTools вкладку Firefox / Chrome Network . И позже я получаю ответ с этого URL-адреса и вручную проверяю, что я получаю, и я нашел csv данные. Но я ожидал, что в этом ответе мне придется извлекать данные из таблицы HTML.

Комментарии:

1. Спасибо. Кажется, я получаю ошибку «HTTP Status 405 Method Not Allowed» с приведенным выше кодом. Чего мне не хватает?

2. как я уже сказал — вероятно, он проверяет файлы cookie, поэтому теперь в ответ я добавил Session() и прочитал ваш исходный URL, прежде чем читать url с данными. Таким образом, он отправляет запрос с файлами cookie. Когда я тестировал старую версию, у меня была открыта исходная страница в браузере, и, возможно, сервер думал, что все в порядке. Но теперь это работает для меня, даже когда я закрываю браузер.

3. этот код кажется нормальным, но если вы все еще получаете ошибку 405, то, возможно, сервер проверяет что-то еще (например, заголовок для запросов XHR) или сервер более ограничен для пользователей из некоторых регионов — я подключаюсь из Польши.

4. Я только что заметил обновленный ответ. Спасибо за редактирование… К сожалению, я все еще получаю ту же ошибку. Возможно, это ограничено для моего региона, или я могу использовать неправильные заголовки. Если есть что-нибудь еще, что я мог бы попробовать, дайте мне знать.