Анализ результатов поиска Reddit с помощью BeautifulSoup и Python

#python #beautifulsoup

#python #beautifulsoup

Вопрос:

Используя Python / BeautifulSoup, я пытаюсь получить заголовок сообщения и URL-адрес из каждого результата, возвращаемого на Reddit.

Ниже приведена часть моего кода, который извлекает все результаты поиска Reddit.

 url = 'https://www.reddit.com/search/?q=test'
r = s.get(url, headers=headers_Get)
soup = BeautifulSoup(r.text, "html.parser")
results = soup.find_all('a', attrs={'data-click-id':'body'})
for result in results:
    print(result.prettify())
    title_post = result.find('h3').text
    url_post = result.find('a')['href']
 

soup.find_all('a', attrs={'data-click-id':'body'}) появляется, чтобы вернуть список всех результатов поиска. Это работает так, как я ожидаю / надеюсь.

делая print(result) это, я могу подтвердить, что он возвращает то, что мне нужно. Ниже приведен результат print(result.prettify()) :

 <a class="SQnoC3ObvgnGjWt90zD9Z _2INHSNB8V5eaWp4P0rY_mE" data-click-id="body" href="/r/Cricket/comments/kunmyt/match_thread_3rd_test_australia_v_india_day_5/">
<div class="_2SdHzo12ISmrC8H86TgSCp _1zpZYP8cFNLfLDexPY65Y7" style="--posttitletextcolor:#222222">
<h3 class="_eYtD2XCVieq6emjKBH3m">
<span style="font-weight:normal">Match Thread: 3rd
<em style="font-weight:700">Test
</em>- Australia v India, Day 5
</span>
</h3>
</div>
</a>
 

title_post = result.find('h3').text извлекает заголовок, связанный с комментарием или сообщением. Он работает так, как ожидалось / надеялся.

Проблема, с которой я сталкиваюсь, заключается в получении адреса сообщения (см. href=):

 <a class="SQnoC3ObvgnGjWt90zD9Z _2INHSNB8V5eaWp4P0rY_mE" data-click-id="body" href="/r/Cricket/comments/kunmyt/match_thread_3rd_test_australia_v_india_day_5/">
 

Строка url_post = result.find('a')['href'] возвращает ошибку TypeError: 'NoneType' object is not subscriptable .

Если бы я мог использовать «результат» как строку, тогда я мог бы просто искать в нем href. Что-то вроде:

 loc = result.text.find('href=')
print(result.text[loc:])
 

Очевидно, что это не сработает:
result.text возвращает не HTML-код, а только строку «Поток соответствия: 3-й тест — Австралия против Индии, день 5″

Вопрос 1. Есть ли способ вернуть только компонент href=»»?

Вопрос 2. Есть ли способ преобразовать объект soup «result» в обычный текст с сохранением компонентов HTML? Если бы это было возможно, у меня был бы простой обходной путь.

Ответ №1:

Уже href находится в .attrs result :

 >>> for result in results:
...     print(result.attrs)
...
{'data-click-id': 'body', 'class': ['SQnoC3ObvgnGjWt90zD9Z', '_2INHSNB8V5eaWp4P0rY_mE'], 'href': '/r/Cricket/comments/kunmyt/match_thread_3rd_test_australia_v_india_day_5/'}
...
 

поэтому не вызывайте .find() метод, вместо этого получите доступ к href значению, используя [key] обозначения (например, словарь).

В вашем примере:

 for result in results:
    url_post = result["href"]
    print(url_post)
 

Вывод:

 /r/Cricket/comments/kunmyt/match_thread_3rd_test_australia_v_india_day_5/
/r/Cricket/comments/ku008u/match_thread_3rd_test_australia_v_india_day_4/
/r/Cricket/comments/ktcg7n/match_thread_3rd_test_australia_v_india_day_3/
...
 

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

1. Спасибо. @MendelG, это то, что я искал.

Ответ №2:

Вы можете использовать PRAW: The Python Reddit API Wrapper для их API, который намного проще в использовании, чем синтаксический анализ с веб-страниц. Очевидно, что вы не можете получить доступ к их случайно сгенерированным именам классов.

https://praw.readthedocs.io/en/latest/

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

1. Спасибо. Я проверю это.