Рубрики
Пример программ на C#

Делаем крутой парсер HTML страниц и парсим пару сайтов

Всем привет,
На просторах интернета я обнаружил один интересный парсер, я добавил описание и немного доработав решил презентовать вам.
Проект объемный поэтому запаситесь терпением.

Лень читать статью вот готовый проект: SuperParser на С#

Поехали,
1) Создаем проект WinForm, назовем его «SuperParser».
2) Сразу заходим в свойства формы и меняем св-ву Text значение на «SuperParser», size выставляем width 800 на height 600 + FormBorderStyle = «FixedSingle»
3) Теперь кидаем на форму listBox, фиксируем его по левому краю, называем его ListTitles(св-во name)
4) Справа кидаем 2 элемента numericUpDown и 2 label к ним, а также 4 кнопки(элемент button)
-первому numbericUpDown меняем св-во name на numericUpDownStart
-второму numbericUpDown меняем св-во name на numericUpDownEnd
-первая кнопку у нас будет подгружать заголовки с сайта habr.ru, поэтому кнопка будет называться buttonHabr, а св-во text=»Habr».
-вторая кнопка у нас будет подгружать заголовки с сайта freelansim.ru, а св-во text=»Freelansim», name=buttonFreelansim
-третья кнопка будет отвечать за очистку listBox, ее назовем buttonClear, а св-во text=»Очистить».
-про четвертую кнопку мы поговорим чуть позже, пока назовем ее «Завершить», а св-во name buttonClose, text=»Завершить»

Форма сейчас выглядит так:
Parser_HTML
5) Так теперь начнем писать ядро нашего парсера, создадим папку в корне проекта и назовем ее Core, все последующие классы и интерфейсы будут храниться в этой папке.
6) Ядро будет состоять из 2 классов(ParserWorker,HtmlLoader) и 2-х интерфейсах (IParser,IParserSettings). Создадим их.
ядро парсера
7) Начнем с интерфейса IParserSettings в нем будет 4 св-в, это фактически настройки будущего парсера — url,динамический постфикс(страницы), в CurrentId будет поставлять id страницы, св-вам StartPoint,EndPoint значение будет присваиваться через конструктор реализующего интерфейс класса. Вот его код

8) Так, самое время подключать библиотеку AngleSharp с помощью который собственно будет распаршивать HTML страницы.
9) Переходим в управление nuget пакетами

10) Устанавливаем библиотеку.

11) Теперь переходим к интерфейсу IParser, это обобщенный интерфейс, в качестве обобщенного параметра указываем T где T — это объект ссылочного типа, интерфейс содержит единственный, но очень важный метод Parse, в него будет передаваться код страницы после чего будет производиться анализ кода и поиск содержимого HTML элементов. Вот его код:

12) Далее переходим в класс HtmlLoader, этот класс будет получать настройки(url и постфикс) и загружать содержимое HTML страницы, я оставил подробные комментарии по коду. Вот собственно код:

13) Теперь займемся самым объемным классом ParserWorker, он будет обобщенным, в качестве обобщенного параметра может использоваться только объект ссылочного типа. Этот класс будет получать код страницы через HtmlLoader, после чего разбирать страницу и возвращать содержимое нужных элементов. Я так же оставил комментарии по коду, на мой взгляд все должно быть понятно, если нет то пишите распишу подробнее. Вот код:

14) Первый сайт который мы будем парсить будет hadr.ru, а спаршивал мы с него будем заголовки.
15) В папке Core создадим папку Habr
16) В ней создадим класс HabrSettings
17) Указываем, что класс будет реализовывать интерфейс IParserSettings

18) Собственно, реализовываем св-ва IParserSettings

19) Так как первая и последняя страница будет указываться из формы нам понадобиться конструктор для инициализации св-ва StartPoint и EndPoint

20) Итого работа над этим классом завершена, выглядит он так.

21) Теперь создаем класс, из которого будем парсить сайт назовем его HabrParser, он у нас будет реализовывать интерфейс IParser, в качестве T у нас будет массив строк.
22) Теперь самое главное, нам нужно зайти на сайт habr.ru и посмотреть в каком элементе хранятся заголовки.
23) Заходим на сайт и нажимаем F12, далее делаем поиск по элементам и получаем результат, заголовки хранятся в class=»post__title_link», который находится в теге <a>

24) Идем обратно в код, пишем следующее:

25) В общем то всё, возвращаемся к форме, для начала объявим переменную типа ParserWorker<string[]> назовем parser_habr, после чего нам предложат добавить using SuperParser.Core; — соглашаемся, а за одно добавим и using SuperParser.Core.Habr;
26) В конструкторе формы после InitializeComponent(); пишем следующее:

27) За конструктором формы реализовываем методы Parser_OnComplited и Parser_OnNewData

28) Теперь необходимо создать обработчик для кнопки Habr, переходим на форму кликаем по ней два раза переходим в код, пишем следующее:

29) В принципе, уже сейчас можно зайти и проверить как парсятся заголовки.
Форма парсера
30) Отлично парсер работает, теперь нужно написать обработчики для кнопок очистить и about, они будут выглядеть так:

31) Теперь по аналогии спарсим заголовки заданий на сайте Freelansim.ru
32) Создаем в папке Core папку Freelansim, а в ней класс FreelansimSettings, который выглядит так:

33) Теперь создает класс FreelansimParser, вот его код:

34) Переходим на форму кликаем 2 раза по кнопке Freelansim,пишем в нее следующее:

35) Теперь поднимаем выше объявляем переменную parser_freelansim  и инициализируем ее по аналогии с parser_habr
парсим freelansim
парсим freelansim
36) Проверяем как парсится freelansim.ru
парсим freelansim

С минимальными изменения с помощью этого парсера можно распарсить практически любой сайт именно так много заморочек с обобщением.
Если дошел до конца, ставь лайк!

59+

13 ответов к “Делаем крутой парсер HTML страниц и парсим пару сайтов”

Да это прям праздник какой то ))) Очень любопытный пример)))) Спасибо за урок. Очень редко встретишь нормальный туториал для парсера на шарпе )))

1+

Большое спасибо. Сейчас все больше людей начинает понимать что C# язык будущего и постепенно начинает появляться много годных примеров.

1+

Не могу разобраться как вывести 2 элемента, допустим не только заголовок, а заголовок и дату публикации.

2+

Приветствую, понимаю, что поздно ответил, но отвечаю на тот случай, если кого то еще это интересует, самый простой способ, внести изменения в HabrParser:
public string[] Parse(IHtmlDocument document)
{
List listPostTime = new List(); //New
List
listHeader = new List(); //Update
List
listResult = new List(); //New

IEnumerable itemsHeaders= document.QuerySelectorAll(«a»)
.Where(item => item.ClassName!= null && item.ClassName.Contains(«post__title_link»));
IEnumerable
itemsPostTime = document.QuerySelectorAll(«*») //New
.Where(item => item.ClassName != null && item.ClassName.Contains(«post__time»));

foreach (var item in itemsHeaders) //Update
{
listHeader.Add(item.TextContent);
}

foreach (var item in itemsPostTime) //New
{
listPostTime.Add(item.TextContent);
}

int counter = 0;
foreach (var item in listHeader) //New
{
listResult.Add(item+»(«+listPostTime[counter]+»)»);
counter++;
}

return listResult.ToArray();
}

0

Я вставляю свой сайт,свои теги. И ничего не работает!В чем причина?

0

В классе ParserWorker ошибка — на 70 строчке retern выйдет из функции и цикл будет выполнен всего один раз

1+

Приветствую, согласен, исправил, так же обратите внимание что baseUrl habr изменился, тоже поправил.

0

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

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

Этот сайт использует Akismet для борьбы со спамом. Узнайте как обрабатываются ваши данные комментариев.