Уведомления

Группа в Telegram: @pythonsu

#1 Авг. 22, 2020 20:15:47

Stargazer
Зарегистрирован: 2020-08-22
Сообщения: 5
Репутация: +  0  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Доброго времени суток. Недавно начал изучать Пайтон. В качестве практики решил написать простой парсер выдачи Bing. Но столкнулся с проблемой.

Итак, мой код выглядит вот так:

 from requests_html import HTMLSession
keywords = [
'как сделать бумажный самолетик',
'как сделать бумажный кораблик',
'как сделать бумажного журавля'
]
session = HTMLSession()
for key in keywords:
    resp = session.get(f'https://www.bing.com/search?q={key}')
    title = resp.html.xpath('//li[@class="b_algo"][1]//h2//text()')
    print(title)

Открываю сессию. В цикле получаю выдачу для каждого из трех ключей и с помощью xpath забираю ТОП-1 выдачи. После этого печатаю результат в консоль.

При этом получаю вот такой результат:
 []
['6 лучших схем бумажных корабликов - Поделки из бумаги']
['Как сложить бумажного журавлика (с иллюстрациями)']

Результата по запросу “как сделать бумажный самолетик” нет. Остальные запросы - ОК.

Если распечатать в файл весь html код страницы, которую парсер получает по первому запросу (файл прилагается) в h1 находиться фраза “Не удалось найти ни одного результата для как сделать бумажный самолетик”.

При этом если зайти по этому адресу из браузера, все впорядке. Результаты показываются.

Подскажите, в чем может быть проблема?

Отредактировано Stargazer (Авг. 22, 2020 20:17:13)

Прикреплённый файлы:
attachment html_как сделать бумажный самолетик.txt (99,5 KБ)

Офлайн

#2 Авг. 23, 2020 00:31:15

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9882
Репутация: +  853  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Stargazer
При этом получаю вот такой результат:
В XPath-запросе указан класс b_algo и тег h2. В файле фраза находится теге li класса b_no и теге h1.

Так что под строкой
  
title = resp.html.xpath('//li[@class="b_algo"][1]//h2//text()')
тебе надо вставить проверку на пустой список. Если он пуст, то надо искать фразу li класса b_no и в теге h1, чтобы убедиться, что она там есть.
Когда ты определил, найден результат/не найден результат/произошла ошибка поиска, ты вставляешь строку в структуру данных для вывода и эту структуру данных для вывода выводишь на экран. Соответственно, твоя структура данных для вывода заполнена тобой, а не текстом со страницы, которого может и не быть, и поэтому на экран всегда выводится всё правильно.

То есть твоя проблема в том, что ты решил код записать кратенько, типа ты профессионал и короткие коды пишешь, а в итоге тебе его теперь надо разделять и работать с ним очень подробно, чтобы код, действительно, правильно написать для начала. Так что не гонись за краткостью, это ничем тебе не поможет. Краткость рождается из длиннющих кодов. Ты сначала пишешь длиннющий код, а потом, когда он готов и отлажен 100500 раз, ты его рефакторишь в краткий код, но который точно такой же по функциональности, как и этот длиннющий. И тогда получается профессиональный код. Но для этого нужно пройти кучу длиннющих кодов и иметь в них кучу опыта, потому что их тоже можно писать совсем не правильно.



Отредактировано py.user.next (Авг. 25, 2020 00:40:00)

Офлайн

#3 Авг. 23, 2020 15:33:43

Stargazer
Зарегистрирован: 2020-08-22
Сообщения: 5
Репутация: +  0  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

py.user.next
Когда ты определил, найден результат/не найден результат/произошла ошибка поиска, ты вставляешь строку в структуру данных для вывода и эту структуру данных для вывода выводишь на экран. Соответственно, твоя структура данных для вывода заполнена тобой, а не текстом со страницы, которого может и не быть, и поэтому на экран всегда выводится всё правильно.

Да, это можно сделать, но мой основной вопрос не в этом.

Я не могу понять почему по одному и тому же адресу - https://www.bing.com/search?q=как+сделать+бумажный+самолетик - браузер получает один html код, а python совершенно другой?

Офлайн

#4 Авг. 23, 2020 22:05:28

ZerG
Зарегистрирован: 2012-04-05
Сообщения: 2627
Репутация: +  61  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Вам нужно понять что вы делаете. И потом сравнить результаты.
Что вы спросили- в питоне - то и получили. браузер имеет ряд других ключей значений и так далее.
Залезьте немного глубже в кроличью нору. Вы на правильном пути.



Влодение рускай арфаграфией - это как владение кунг-фу: настаящие мастира не преминяют ево бес ниабхадимости

Офлайн

#5 Авг. 23, 2020 23:50:29

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9882
Репутация: +  853  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Stargazer
Я не могу понять почему по одному и тому же адресу - https://www.bing.com/search?q=как+сделать+бумажный+самолетик - браузер получает один html код, а python совершенно другой?
Потому что в браузере ещё работает движок JavaScript. И когда ты загружаешь страницу, на странице есть не только текст, но и указания для браузеров загружать и запускать внутри себя определённые скрипты. А эти скрипты имеют полный доступ к документу, который и отображается браузером у тебя в итоге. То есть не страница отображается, которую ты скачал, а всё вместе собирается в единый документ в оперативной памяти, который потом и отображается. Соответственно, что-то берётся из исходника страницы, что-то устанавливается скриптами. Поэтому на странице могут быть поля пустыми, а в браузере будет показывать текст в этих полях.

Но это всё не относится к твоей проблеме парсинга. У тебя, когда результат не найден и для его вывода используются другие теги, ты пытаешься его разобрать как найденный результат по тегам найденного результата.



Отредактировано py.user.next (Авг. 23, 2020 23:52:05)

Офлайн

#6 Авг. 24, 2020 16:49:01

Stargazer
Зарегистрирован: 2020-08-22
Сообщения: 5
Репутация: +  0  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

py.user.next
У тебя, когда результат не найден и для его вывода используются другие теги, ты пытаешься его разобрать как найденный результат по тегам найденного результата.

Не могу понять. Поясни пожалуйста.

Офлайн

#7 Авг. 25, 2020 00:18:35

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9882
Репутация: +  853  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Stargazer
py.user.next
У тебя, когда результат не найден и для его вывода используются другие теги, ты пытаешься его разобрать как найденный результат по тегам найденного результата.
Не могу понять. Поясни пожалуйста.
Вот твой XPath-запрос
Stargazer
  
title = resp.html.xpath('//li[@class="b_algo"][1]//h2//text()')
Вот твой файл с ненайденными результатами
https://python.su/forum/attachment/4743760b048605a93010a0767175095272d1d5b0/

А теперь найди в этом файле b_algo, h2 и текст внутри h2.



Отредактировано py.user.next (Авг. 25, 2020 00:35:46)

Офлайн

#8 Авг. 25, 2020 10:46:53

Stargazer
Зарегистрирован: 2020-08-22
Сообщения: 5
Репутация: +  0  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

py.user.next
А теперь найди в этом файле b_algo, h2 и текст внутри h2

Дак его там и нет. В этом то и вопрос. Питон получает html в котором нет результатов выдачи. А браузер получает по этому же запросу код с выдачей.

При этом, результаты двух других запросов в браузере и питоне совпадают. Я пытаюсь понять почему так.

Проблема в Java Script? Но библиотека html-requests насколько я понимаю поддерживает работу с JS. Только я не пойму как эту поддержку реализовать. На главной странице библиотеки https://requests-html.kennethreitz.org/ есть пример кода:

 >>> r = session.get('http://python-requests.org/')
>>> r.html.render()
>>> r.html.search('Python 2 will retire in only {months} months!')['months']
'<time>25</time>'

Получается мне нужно добавить resp.html.render() к запросу. Я попробовал, но это не помогает. Что я делаю не так?

Офлайн

#9 Авг. 25, 2020 14:00:09

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9882
Репутация: +  853  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Stargazer
Дак его там и нет. В этом то и вопрос. Питон получает html в котором нет результатов выдачи. А браузер получает по этому же запросу код с выдачей.
Попробовал это сделать. Вот как говорил здесь, так оно и обстоит.

  
#!/usr/bin/env python3
 
from requests_html import HTMLSession
 
keywords = [
    'как сделать бумажный самолетик',
    'как сделать бумажный кораблик',
    'как сделать бумажного журавля'
]
 
session = HTMLSession()
for key in keywords:
    resp = session.get(f'https://www.bing.com/search?q={key}')
    search_result = resp.html.xpath('//li[@class="b_algo"][1]//h2//text()')
    if search_result:
        nodes = [i.encode('latin1').decode('utf-8') for i in search_result]
        result = (True, ''.join(nodes))
    else:
        nodes = resp.html.xpath('//li[@class="b_no"][1]//h1//text()')
        result = (False, ''.join(nodes))
    status, title = result
    fmt = 'Result: {:4} Request: {}\n    {}'
    print(fmt.format(('FAIL', 'OK')[status], key, title))
[guest@localhost bingsearch]$ ./bingsearch.py 
Result: FAIL Request: как сделать бумажный самолетик
Не удалось найти ни одного результата для как сделать бумажный самолетик
Result: OK Request: как сделать бумажный кораблик
Кораблик из бумаги: 10 вариантов, 120 фото как сделать ...
Result: OK Request: как сделать бумажного журавля
Как сложить бумажного журавлика (с иллюстрациями)
[guest@localhost bingsearch]$



Отредактировано py.user.next (Авг. 25, 2020 14:02:02)

Офлайн

#10 Авг. 25, 2020 22:21:35

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9882
Репутация: +  853  -
Профиль   Отправить e-mail  

Проблема с парсингом Бинг

Добавив печенье, которое я взял из браузера, я получил найденные результаты.

  
#!/usr/bin/env python3
 
from requests_html import HTMLSession
 
keywords = [
    'как сделать бумажный самолетик',
    'как сделать бумажный кораблик',
    'как сделать бумажного журавля'
]
 
session = HTMLSession()
for key in keywords:
    cookie = ('_EDGE_S=F=1&SID=28A75AD8CBCA62A8303855E9CA1863C3;'
              ' _EDGE_V=1; MUID=29136B8A85066B00244864BB84D46AA3; '
              'SRCHD=AF=NOFORM; '
              'SRCHUID=V=2&GUID=C0FFD0A5EA3A49BB9F70BDDD40C53F2D&dmnchg=1; '
              'SRCHUSR=DOB=20200825; '
              '_SS=SID=28A75AD8CBCA62A8303855E9CA1863C3; '
              '_HPVN=CS=eyJQbiI6eyJDbiI6MSwiU3QiOjAsIlFzIjowLCJQcm9kIjoiUC'
              'J9LCJTYyI6eyJDbiI6MSwiU3QiOjAsIlFzIjowLCJQcm9kIjoiSCJ9LCJRe'
              'iI6eyJDbiI6MSwiU3QiOjAsIlFzIjowLCJQcm9kIjoiVCJ9LCJBcCI6dHJ1'
              'ZSwiTXV0ZSI6dHJ1ZSwiTGFkIjoiMjAyMC0wOC0yNVQwMDowMDowMFoiLCJ'
              'Jb3RkIjowLCJEZnQiOm51bGwsIk12cyI6MCwiRmx0IjowLCJJbXAiOjJ9; '
              'MUIDB=29136B8A85066B00244864BB84D46AA3')
    resp = session.get(f'https://www.bing.com/search?q={key}', headers={'Cookie': cookie})
    search_result = resp.html.xpath('//li[@class="b_algo"][1]//h2//text()')
    if search_result:
        nodes = [i.encode('latin1').decode('utf-8') for i in search_result]
        result = (True, ''.join(nodes))
    else:
        nodes = resp.html.xpath('//li[@class="b_no"][1]//h1//text()')
        result = (False, ''.join(nodes))
    status, title = result
    fmt = 'Result: {:4} Request: {}\n    {}'
    print(fmt.format(('FAIL', 'OK')[status], key, title))
[guest@localhost bingsearch]$ ./bingsearch.py 
Result: OK Request: как сделать бумажный самолетик
Как сделать далеко летающий самолет из бумаги. Оригами ...
Result: OK Request: как сделать бумажный кораблик
Кораблик из бумаги: 10 вариантов, 120 фото как сделать ...
Result: OK Request: как сделать бумажного журавля
Как сложить бумажного журавлика (с иллюстрациями)
[guest@localhost bingsearch]$



Отредактировано py.user.next (Авг. 25, 2020 22:22:46)

Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version