Парсер лучших за сутки статей habr(а) на Python. Очень подробно и просто

от автора

Во-первых, я начинающий программист.

Во-вторых давайте приступим.

Нужные нам библиотеки (вставляем в командную строку, либо в терминале или куда вам удобно):

pip install beautifulsoup4 pip install requests pip install fake-useragent

Инициализируем модули в наш заранее созданный проект, т.е. файл с расширением py.

from bs4 import BeautifulSoup import random import json import requests import datetime from fake_useragent import UserAgent

Создаем переменную с модулем fake_useragent, чтобы мы могли потом использовать для генерации user-agent:

ua = UserAgent()

Определяем заголовки (для того чтобы сервер сайта мог понять, как он должен отправить ответ, а также помогает серверу определить отправителя запроса)

headers = {     'accept': 'application/json, text/plain, */*',     'user-Agent': ua.google, }

Создаем словарь, где будут храниться название и ссылка на каждую статью:

article_dict = {}

Создаем цикл для сбора со всех страниц, а не с одной (с 1 по 3, т.к. страниц с ссылками в день, как я понимаю всего 3).

for i in range(1, 4):

Указываем url c форматирование кода, где i — номер страницы, которое вставляться при каждом проходе цикла.

url = f'https://habr.com/ru/top/daily/page{i}/'

Отправляем get запрос на сайт, указывая в первом аргументе — переменную с url сайта, во-втором заголовки. Атрибут text, нужен чтобы получить текстовое содержанием html страницы.

req = requests.get(url, headers=headers).text

Теперь с помощью BeautifulSoup соберем весь html код страницы.

soup = BeautifulSoup(req, 'lxml')

Если попробовать вывести такой код с помощью print(soup), выведется весь html код страницы.

Далее, используя наш «soup» созданный в прошлом шаге, с помощью метода find_all собираем все ссылки с помощью тега «a» в первом аргументе, во-втором, с помощью F12, ищем класс у всех ссылок наших статей, как мы видим это — tm-article-snippet__title-link.

a - это тег, после точки - класс тега.
a — это тег, после точки — класс тега.
all_hrefs_articles = soup.find_all('a', class_='tm-article-snippet__title-link')

Класс указывается с нижним подчеркиванием, т.к. это ключевое (зарезервированное) слово в Python.

Создаем еще один цикл, где мы будем проходиться по всем статьям собранных в переменной all_hrefs_articles.

В теге «a» с классом «tm-article-snippet__title-link» находится еще один тег «span» c нашими именами ссылок, получим его с помощью метода find.

article_name = article.find('span').text # собираем названия статей

Теперь получим ссылку на статью, указываем что это f строка, и с помощью get запроса в скобочках получаем атрибут «href» — основной атрибут тега «a».

article_link = f'https://habr.com{article.get("href")}'

Получается ссылка, например: «https://habr.com/ru/company/tinkoff/blog/715604/»

Теперь указываем пару ключ — значение для названия и ссылку на статью (для нашего словаря):

article_dict[article_name] = article_link

Выходим из обоих циклов. С помощью конструкции «with open» создаем файл articles_ + дата и время создания файла с помощью модуля datetime, который мы импортировали, файл создаем с расширением .json (ну мне так удобнее), следующее мы указываем ‘w’, что означает, что нужно создать файл с таким-то названием и вписать следующий код, который мы укажем внутри файла, также указываем кодировку » encoding =’utf-8′ «, чтобы файл мог отобразить русские символы.

with open(f"articles_{datetime.datetime.now().strftime('%d_%m_%Y')}.json", "w", encoding='utf-8') as f: 

Создаем конструкцию try, except (если нет ошибок при парсинге, выводится try, если выводится ошибка при парсинге => except)

try:  except:   

В try, мы «говорим», чтобы в json файл отправлялись данные, 1 — словарь с нашими статьями , 2 — имя файла, куда отправлять данные (в открытии файла мы указали в конце его как f, чтобы с ним можно было работать), 3 — отступы (я сделал 4 для удобства чтения, можно указать свое), 4 — экранирование ASCII символов, и следующей строкой вывод, что статьи успешно были получены.

print('Статьи были успешно получены')

В except, мы выводим, что статьи не удалось получить и нужно искать проблемы в коде.

print('Статьи были успешно получены')

В конечном итоге, должно получиться что-то похожее:

from bs4 import BeautifulSoup import random import json import requests import datetime from fake_useragent import UserAgent  ua = UserAgent()  headers = {     'accept': 'application/json, text/plain, */*',     'user-Agent': ua.google, }  article_dict = {}  for i in range(1, 4):     url = f'https://habr.com/ru/top/daily/page{i}/'      req = requests.get(url, headers=headers).text      soup = BeautifulSoup(req, 'lxml')     all_hrefs_articles = soup.find_all('a', class_='tm-article-snippet__title-link') # получаем статьи      for article in all_hrefs_articles: # проходимся по статьям         article_name = article.find('span').text # собираем названия статей         article_link = f'https://habr.com{article.get("href")}' # ссылки на статьи         article_dict[article_name] = article_link  with open(f"articles_{datetime.datetime.now().strftime('%d_%m_%Y')}.json", "w", encoding='utf-8') as f:      try:             json.dump(article_dict, f, indent=4, ensure_ascii=False)         print('Статьи были успешно получены')     except:         print('Статьи не удалось получить')


ссылка на оригинал статьи https://habr.com/ru/post/717556/


Комментарии

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *