private void ParseOffersListPage(IHtmlDocument searchPageDOM, string regionLink) { UpdateInternalProxy(); Console.WriteLine("Текущий прокси: " + currentProxy.Address); var links = searchPageDOM.QuerySelectorAll(".result-title.hdrlnk"); List <IElement> linksList = new List <IElement>(links.ToList()); for (int i = 0; i < linksList.Count; i++) // "craigslist.org" в ссылке - явный индикатор альтернативного предложения из другого региона { if (links[i].GetAttribute(Constants.WebAttrsNames.href).Contains("craigslist.org")) { Console.WriteLine(links[i].GetAttribute("href")); linksList.RemoveRange(i, linksList.Count - 1 - i); break; } } SqlCommand insertOfferCommand = DataProvider.Instance.CreateSQLCommandForInsertSP(); insertOfferCommand.Connection = DataProvider.Instance.Connection; insertOfferCommand.Connection.Open(); for (int i = 0; i < linksList.Count; i++) { Offer o = ParseOffer(parser.Parse(WebHelpers.GetHtmlThrowProxy(regionLink + linksList[i].GetAttribute(Constants.WebAttrsNames.href), currentProxy))); //теперь парсим каждую отдельную ссылку(предложение) if (o != null) { InsertIntoDB(o, insertOfferCommand);//запихиваем предложение в БД } else { //File.AppendAllText("log.txt", String.Format("Не спарсилось: {0},{1}\n", regionLink + links[i].GetAttribute(Constants.WebAttrsNames.href), DateTime.Now)); //если не спарсилось, заносим в лог } } insertOfferCommand.Connection.Close(); }
/// <summary> /// Парсит регион сайта CraigsList /// </summary> /// <param name="regionLink">Полный адрес сайта региона для выборки</param> public void StartParsing(string regionLink, int minPrice, int maxPrice) { string searchPageInline = Constants.WebAttrsNames.NotFound; for (int i = 0; i < 3; i++) { searchPageInline = WebHelpers.GetHtmlThrowProxy(CompileLink(regionLink, Resources.HouseSearchLinkPostfix, minPrice, maxPrice), currentProxy); //парсим обычным образом if (searchPageInline == Constants.WebAttrsNames.NotFound) //, а если не получится, пробуем по другому постфиксу(для некоторых регионов { searchPageInline = WebHelpers.GetHtmlThrowProxy(CompileLink(regionLink, Resources.AltHouseSearchLinkPostfix, minPrice, maxPrice), currentProxy); if (searchPageInline != Constants.WebAttrsNames.NotFound) { break; } } else { break; } UpdateInternalProxy(); } var searchPageDOM = parser.Parse(searchPageInline); //получаем стартовую страницу выдачи нужных предложений. //проверяем, равно ли число общей выдачи для нашей ссылки 2500(максимальный) var totalcountElement = searchPageDOM.QuerySelector(".totalcount"); if (totalcountElement != null) //если не отсутствует(это если результатов нет вообще), тогда проверим на 2500 { if (totalcountElement.TextContent == "2500") { if (maxPrice == Constants.PriceValues.undefinedValue || maxPrice == Constants.PriceValues.undefinedValue) { maxPrice = 1000000; minPrice = 0; } if (maxPrice != minPrice) { int Average = (maxPrice + minPrice) / 2; StartParsing(regionLink, minPrice, Average); StartParsing(regionLink, Average + 1, maxPrice); return; } } } AngleSharp.Dom.IElement searchResultNextPageLink = null; try { searchResultNextPageLink = searchPageDOM.QuerySelector("a.button.next"); } catch (Exception e) { Console.WriteLine(e.Message); } //парсим результаты на текущей странице if (searchResultNextPageLink != null) { string oldSearchResultNextPageLinkstring = "="; do { Console.WriteLine("Начинаем парсить страницу выдачи: {0}{1}", regionLink, searchResultNextPageLink.GetAttribute(Constants.WebAttrsNames.href)); ParseOffersListPage(searchPageDOM, regionLink); //парсим предложения этой страницы Console.WriteLine("Спарсили текущую страницу выдачи!"); var offersListPageHtmlDocument = parser.Parse(WebHelpers.GetHtmlThrowProxy(regionLink + searchResultNextPageLink.GetAttribute(Constants.WebAttrsNames.href), currentProxy)); //получаем DOM-документ одной страницы выдачи предложений searchResultNextPageLink = offersListPageHtmlDocument.QuerySelector("a.button.next"); //берем элемент со ссылкой на следующую страницу if (searchResultNextPageLink == null) { break; } else { if (WrongLink(searchResultNextPageLink, oldSearchResultNextPageLinkstring)) //проверяем, а не ушли ли мы в цикл { break; //если мы в цикле, тогда хватит парсить ту же страницу до бесконечности } else { oldSearchResultNextPageLinkstring = searchResultNextPageLink.GetAttribute(Constants.WebAttrsNames.href); //новая ссылка для будущих итераций } } Console.WriteLine(searchResultNextPageLink != null ? "Получено:" + regionLink + searchResultNextPageLink.GetAttribute(Constants.WebAttrsNames.href) : "На этой странице нет результатов и ссылок на следующую страницу!"); if (searchResultNextPageLink != null) { searchPageDOM = parser.Parse(WebHelpers.GetHtmlThrowProxy(regionLink + searchResultNextPageLink.GetAttribute(Constants.WebAttrsNames.href), currentProxy)); } Console.WriteLine("------------------------------------------"); } while (searchResultNextPageLink != null); } else { Console.WriteLine("Nothing to parse"); UpdateInternalProxy(); //File.AppendAllText("log.txt", String.Format("Регион не спарсился или там нет предложений жилья: {0}, {1}\n", regionLink, DateTime.Now)); //если не спарсилось, заносим в лог string UnsecureRegionLink = regionLink.Replace("https", "http"); if (regionLink.Length != UnsecureRegionLink.Length) { StartParsing(UnsecureRegionLink, minPrice, maxPrice); } } Console.WriteLine("Регион " + regionLink + "обработан!"); //File.AppendAllText("log.txt", String.Format("Регион обработан: {0}, {1}\n", regionLink, DateTime.Now)); //Console.ReadKey(); }
private bool ExcludeProxyByTestLink(WebProxy i) { return(WebHelpers.GetHtmlThrowProxy(Resources.StartLink, i) == Constants.WebAttrsNames.NotFound ? true : false); }