예제 #1
0
        private void ParsePage(string url)
        {
            if (!_db.Connect())
            {
                MessageBox.Show(General.ERROR_DB_CONNECT);
                _db.Close();
                Invoke(new Action(() =>
                {
                    startButton.Text    = "Начать";
                    startButton.Enabled = true;
                    statusLabel.Text    = General.STATUS_DEFAULT;
                }));
                return;
            }

            /*
             * Трём '#' и всё после него, если таковой есть
             */
            var shard_idx = url.IndexOf("#");

            if (shard_idx > -1)
            {
                url = url.Remove(shard_idx);
            }
            //
            Invoke(new Action(() =>
            {
                textBox1.Text = url;
            }));
            //

            var  lastId   = _db.GetLastID() + 1;
            var  siteType = General.GetSiteType(url);
            uint cnt      = 0;

            if (siteType == SiteType.Farpost)
            {
                if (url.Contains("status=archive"))
                {
                    _archiveFlag = true;
                }
                else
                {
                    _archiveFlag = false;
                }
                var singleType = Farpost.GetTypeByLink(url);
                var dateTime   = DateTime.Now.ToString("yyyyMMdd_HHmmss");
                var folderName = dateTime + "_" + singleType + (_archiveFlag ? "_arc" : string.Empty);
                var workingDir = General.FARPOST_FOLDER + folderName + "\\";
                var Comment    = (CommentBox.Text != String.Empty ? CommentBox.Text.Replace(" ", "_") : string.Empty);
                Directory.CreateDirectory(workingDir);
                List <Advertisement> advsData;
                var saveTo  = workingDir + "L_" + dateTime + "_" + (_archiveFlag ? "_arc" : string.Empty) + singleType + ".html";
                var typeInt = _db.GetAdvTypeByString(singleType);
                if (url.Contains("?page=") || url.Contains("&page="))
                {
                    Invoke(new Action(() =>
                    {
                        statusLabel.Text = "Собираем информацию с ленты...";
                    }));
                    advsData = Farpost.GetDataFromFeed(url, saveTo);
                    _db.InsertPageInfo(saveTo, typeInt, lastId, lastId + advsData.Count - 1, DateTime.Now.ToString("yyyy.dd.MM hh:mm:ss"));
                }
                else
                {
                    var pages = Farpost.GetItemsCount(url);
                    pages = (int)Math.Ceiling((float)(pages / 50)) + 1;
                    if (pages != 1)
                    {
                        Invoke(new Action(() =>
                        {
                            statusLabel.Text = "Собираем информацию со всех страниц ленты (0/" + pages + ")...";
                        }));
                        advsData = new List <Advertisement>();
                        for (var i = 1; i <= pages; i++)
                        {
                            if (_stopFlag)
                            {
                                break;
                            }
                            saveTo = workingDir + "L_" + dateTime + "_" + (_archiveFlag ? "_arc" : string.Empty) + singleType + "_" + i + ".html";
                            var urlp = url + (url.Contains("?") ? "&" : "?") + "page=" + i;
                            var temp = Farpost.GetDataFromFeed(urlp, saveTo);

                            advsData.AddRange(temp);
                            _db.InsertPageInfo(saveTo, typeInt, lastId, lastId + advsData.Count - 1, DateTime.Now.ToString("yyyy.dd.MM hh:mm:ss"));
                            Invoke(new Action(() =>
                            {
                                statusLabel.Text = "Собираем информацию со всех страниц ленты (" + i + "/" + pages + ")...";
                            }));
                            if (pages != i)
                            {
                                General.SmallDelay();
                            }
                        }
                    }
                    else
                    {
                        Invoke(new Action(() =>
                        {
                            statusLabel.Text = "Собираем информацию с ленты...";
                        }));
                        advsData = Farpost.GetDataFromFeed(url, saveTo);
                        _db.InsertPageInfo(saveTo, typeInt, lastId, lastId + advsData.Count - 1, DateTime.Now.ToString("yyyy.dd.MM hh:mm:ss"));
                    }
                }
                if (_stopFlag)
                {
                    _db.Close();
                    Invoke(new Action(() =>
                    {
                        startButton.Text    = "Начать";
                        startButton.Enabled = true;
                        statusLabel.Text    = General.STATUS_DEFAULT;
                    }));
                    return;
                }
                if (advsData == null || advsData.Count == 0)
                {
                    MessageBox.Show("Не удалось собрать объявления с указаной страницы.");
                    _db.Close();
                    Invoke(new Action(() =>
                    {
                        startButton.Text    = "Начать";
                        startButton.Enabled = true;
                        statusLabel.Text    = General.STATUS_DEFAULT;
                    }));
                    return;
                }
                cnt = 0;
                Invoke(new Action(() =>
                {
                    listBox1.Items.Clear();
                }));
                Invoke(new Action(() =>
                {
                    statusLabel.Text = "Обработка данных...";
                }));
                var todel   = new List <Advertisement>();
                var updated = new List <int>();
                var trigger = checkBox1.Checked;
                int newId   = lastId;
                for (var i = 0; i < advsData.Count; i++)
                {
                    if (_stopFlag)
                    {
                        break;
                    }
                    var id = _db.GetIdByNumber(advsData[i].Number);
                    if (id != -1) // Если объява с таким внутренним идом уже существует, то
                    {
                        // Получаем информацию о ней. И если цена и площадь остались прежними - удаляем из списка на инсерты данную великолепную запись.
                        var adv = _db.GetAdvPdata(id);
                        if ((!trigger && General.GetNumbers(adv.Price) == General.GetNumbers(advsData[i].Price) && General.GetNumbers(adv.Square) == General.GetNumbers(advsData[i].Square) ||
                             (trigger && General.GetNumbers(adv.Price) == General.GetNumbers(advsData[i].Price) && General.GetNumbers(adv.Square) == General.GetNumbers(advsData[i].Square) && _db.GetTownByMainId(id) == -1 && _db.GetTownByMainId(id) == 0)))
                        {
                            todel.Add(advsData[i]);
                            continue;
                        }
                        updated.Add(newId);
                    }

                    _db.InsertRecord();
                    newId++;
                }
                foreach (var item in todel)
                {
                    advsData.Remove(item);
                }
                string distr = String.Empty;
                if (advsData.Count > 0)
                {
                    foreach (var advData in advsData)
                    {
                        if (_stopFlag)
                        {
                            break;
                        }
                        Invoke(new Action(() =>
                        {
                            listBox1.Items.Add(advData.Link);
                            countLabel.Text = "Кол-во объявлений: " + ++cnt;
                        }));
                        if (advData.Annotations != null)
                        {
                            foreach (string item in advData.Annotations)
                            {
                                if (item.Contains("р-н"))
                                {
                                    distr = item;
                                    break;
                                }
                            }
                        }
                        var dir    = workingDir + lastId + "_" + advData.Number + "_" + DateTime.Now.ToString("yyyyddMM_hhmmss") + (_archiveFlag ? "_arc" : string.Empty);
                        var newdir = workingDir.Trim('\\') + "_" + advsData.Count + Comment;
                        int is_new = 1;
                        if (updated.Contains(lastId))
                        {
                            is_new = 0;
                        }
                        int source = 1;
                        if (_archiveFlag)
                        {
                            source = 2;
                        }
                        _db.UpdateAdvData(lastId, is_new, source, advData.Number, advData.Link, "www.farpost.ru", newdir, advData.CurLink, advData.Title, advData.Price, advData.Square, advData.Geo, advData.City, distr, advData.Views, typeInt);
                        _db.InsertSecData(lastId);
                        Directory.CreateDirectory(dir);
                        lastId++;
                    }
                    if (singleType.Contains("КН_") && !(url.Contains("&flatType") || url.Contains("?flatType")))
                    {
                        var commercialTypes = new string[][] {
                            new [] { "outlet", "Торговая точка" },
                            new [] { "manufacture", "Производство" },
                            new [] { "office", "Офис" },
                            new [] { "storage", "Склад" },
                            new [] { "etc", "Другое" },
                        };
                        var advsDataAd = new List <Advertisement>();
                        foreach (var commercialType in commercialTypes)
                        {
                            var urlp  = url + (url.Contains("?") ? "&" : "?") + "flatType%5B%5D=" + commercialType[0];
                            var pages = Farpost.GetItemsCount(urlp);
                            pages = (int)Math.Ceiling((float)(pages / 50)) + 1;
                            if (pages != 1)
                            {
                                for (var i = 1; i <= pages; i++)
                                {
                                    if (_stopFlag)
                                    {
                                        break;
                                    }
                                    var paged = urlp + (urlp.Contains("?") ? "&" : "?") + "page=" + i;
                                    var temp  = Farpost.GetDataFromFeed(paged, null);
                                    advsDataAd.AddRange(temp);
                                    if (pages != i)
                                    {
                                        General.SmallDelay();
                                    }
                                }
                            }
                            else
                            {
                                advsDataAd = Farpost.GetDataFromFeed(urlp, null);
                            }
                            foreach (var advDataAd in advsDataAd)
                            {
                                _db.UpdateComType(advDataAd.Number, commercialType[1]);
                            }
                        }
                    }
                }
                var newPath = workingDir.Trim('\\') + "_" + advsData.Count + "_" + Comment;
                Directory.Move(workingDir, newPath);
                _lastSaveToPath = newPath;
            }
            else if (siteType == SiteType.Cian)
            {
                var links = Cian.GetLinksFromFeed(url);
                if (links == null)
                {
                    MessageBox.Show("Не удалось собрать ссылки на объявления с указаной страницы.");
                    _db.Close();
                    Invoke(new Action(() =>
                    {
                        startButton.Text    = "Начать";
                        startButton.Enabled = true;
                        statusLabel.Text    = General.STATUS_DEFAULT;
                    }));
                    return;
                }
                cnt = 0;
                Invoke(new Action(() =>
                {
                    listBox1.Items.Clear();
                }));
                foreach (var link in links)
                {
                    if (string.IsNullOrEmpty(link))
                    {
                        continue;
                    }
                    Invoke(new Action(() =>
                    {
                        listBox1.Items.Add(link);
                        countLabel.Text = "Кол-во объявлений: " + ++cnt;
                    }));
                    General.Delay();
                }
            }
            _db.Close();
            Invoke(new Action(() =>
            {
                startButton.Text    = "Начать";
                startButton.Enabled = true;
                statusLabel.Text    = General.STATUS_DEFAULT;
            }));
        }
예제 #2
0
        private void UploadAdvs()
        {
            if (!_db.Connect())
            {
                MessageBox.Show(General.ERROR_DB_CONNECT);
                _db.Close();
                Invoke(new Action(() =>
                {
                    statusLabel.Text      = STATUS_BAR_DEFAULT;
                    uploadButton.Enabled  = true;
                    exploreButton.Enabled = true;
                    parseButton.Enabled   = true;
                    exportButton.Enabled  = true;
                    textBox2.Enabled      = true;
                    stopButton.Enabled    = false;
                    fromBox.Enabled       = true;
                    toBox.Enabled         = true;
                }));
                return;
            }

            var targets = textBox2.Text.Split(';');
            var i       = 0;

            foreach (var target in targets)
            {
                var paths = Directory.GetDirectories(target);
                Invoke(new Action(() =>
                {
                    statusLabel.Text = "Инициализация Selenium...";
                }));
                IWebDriver browser;
                var        option = new ChromeOptions();
                option.AddArgument("--headless");
                option.AddArgument("--user-agent=" + General.DEFAULT_USER_AGENT);
                //option.AddArgument("--proxy-server=socks5://109.234.35.41:8888");
                var service = ChromeDriverService.CreateDefaultService();
                service.HideCommandPromptWindow = true;
                browser = new ChromeDriver(service, option);
                // Нужно сделать проверку является-ли фарпостовской сессией
                var defaultPageAddress = "https://www.farpost.ru/vladivostok/realty/sell_flats/?page=1";
                browser.Navigate().GoToUrl(defaultPageAddress);
                var def = (int)(toBox.Value - fromBox.Value) + 1;
                foreach (var path in paths)
                {
                    if (_stopFlag)
                    {
                        break;
                    }
                    var pathSplit = path.Split('\\');
                    var advName   = pathSplit[pathSplit.Length - 1];
                    var nlink     = target + "\\" + advName;
                    if (File.Exists(nlink + ".html") || File.Exists(nlink + "_arch.html"))
                    {
                        i++;
                        continue;
                    }
                    var idStr = pathSplit[pathSplit.Length - 1].Split('_')[0];
                    if (!int.TryParse(idStr, out int id))
                    {
                        i++;
                        continue;
                    }
                    if (id < fromBox.Value || id > toBox.Value)
                    {
                        i++;
                        continue;
                    }
                    Invoke(new Action(() =>
                    {
                        statusLabel.Text = "Загрузка объявления #" + idStr + " [" + i + "/" + def + "]";
                    }));
                    var link = _db.GetLinkById(id);
                    while (true)
                    {
                        if (_stopFlag)
                        {
                            break;
                        }
                        try
                        {
                            browser.Navigate().GoToUrl(link);
                            if (browser.PageSource.Contains("Из вашей подсети наблюдается подозрительная активность"))
                            {
                                _db.Close();
                                Invoke(new Action(() =>
                                {
                                    statusLabel.Text      = STATUS_BAR_DEFAULT;
                                    uploadButton.Enabled  = true;
                                    exploreButton.Enabled = true;
                                    parseButton.Enabled   = true;
                                    exportButton.Enabled  = true;
                                    textBox2.Enabled      = true;
                                    stopButton.Enabled    = false;
                                    fromBox.Enabled       = true;
                                    toBox.Enabled         = true;
                                }));
                                service.Dispose();
                                browser.Dispose();
                                MessageBox.Show("Капча! Завершаем работу.");
                                return;
                            }
                            break;
                        }
                        catch (Exception ex)
                        {
                            General.WriteLog(ex.Message);
                            Thread.Sleep(10000);
                        }
                    }
                    if (!browser.PageSource.Contains("Объявление находится в архиве и может быть неактуальным."))
                    {
                        for (var k = 0; k < 5; k++)
                        {
                            if (_stopFlag)
                            {
                                break;
                            }
                            try
                            {
                                var element = browser.FindElement(By.PartialLinkText("Показать контакты"));
                                element.Click();
                                var isf = false;
                                for (var ti = 0; ti < 20 && !_stopFlag; ti++)
                                {
                                    try
                                    {
                                        browser.FindElement(By.ClassName("dummy-listener_new-contacts"));
                                        isf = true;
                                        break;
                                    }
                                    catch
                                    {
                                        Thread.Sleep(500);
                                    }
                                }
                                if (isf)
                                {
                                    break;
                                }
                            }
                            catch (Exception ex)
                            {
                                General.WriteLog(ex.Message);
                                Thread.Sleep(1000);
                            }
                        }
                    }
                    else
                    {
                        nlink += "_arch";
                    }
                    try
                    {
                        var element = browser.FindElement(By.ClassName("expand--button"));
                        element.Click();
                        for (var ti = 0; ti < 20 && !_stopFlag; ti++)
                        {
                            try
                            {
                                browser.FindElement(By.ClassName("mod__active"));
                                break;
                            }
                            catch
                            {
                            }
                            Thread.Sleep(1000);
                        }
                    }
                    catch (Exception)
                    {
                    }
                    var content = browser.PageSource;


                    var images = new List <string>();
                    var doc    = new HtmlAgilityPack.HtmlDocument();
                    doc.LoadHtml(content);
                    var nodes = doc.DocumentNode.SelectNodes("//img");
                    if (nodes != null)
                    {
                        var nodesArray = nodes.ToArray();
                        foreach (var node in nodesArray)
                        {
                            images.Add(node.Attributes["src"].Value);
                        }
                    }

                    int img_name = 0;
                    using (var wc = new WebClient())
                    {
                        foreach (var imageSrc in images)
                        {
                            if (_stopFlag)
                            {
                                break;
                            }
                            try
                            {
                                var ext = imageSrc;
                                var idx = ext.LastIndexOf("/");
                                if (idx == -1)
                                {
                                    continue;
                                }
                                ext = ext.Remove(0, idx + 1);
                                idx = ext.LastIndexOf(".");
                                ext = idx != -1 ? ext.Remove(0, idx) : ".jpg";
                                var pictureName = img_name.ToString() + ext;

                                content = content.Replace(imageSrc, Path.Combine(advName, pictureName));
                                wc.DownloadFile(imageSrc, Path.Combine(path, pictureName));
                                img_name++;
                            }
                            catch (Exception ex)
                            {
                                General.WriteLog(ex.Message);
                            }
                        }
                    }
                    nodes = doc.DocumentNode.SelectNodes("//*[href]");
                    if (nodes != null)
                    {
                        var nodesArray = nodes.ToArray();
                        foreach (var node in nodesArray)
                        {
                            var value = node.Attributes["href"].Value;
                            if (!value.StartsWith("http://") && !value.StartsWith("https://"))
                            {
                                var newValue = value;
                                if (newValue.StartsWith("/"))
                                {
                                    newValue.Remove(0, 1);
                                }
                                content = content.Replace(value, "https://www.farpost.ru/" + newValue);
                            }
                        }
                    }

                    var htmled = nlink + ".html";
                    File.WriteAllText(htmled, content, Encoding.UTF8);
                    FileInfo fileInfo = new FileInfo(htmled);
                    string   newname;
                    if (fileInfo.Length <= 25600)
                    {
                        newname = nlink + "_udalen.html";
                        File.Move(htmled, newname);
                    }
                    _db.ChangeAdvNLink(id, htmled);
                    General.Delay();
                    i++;
                }
                _db.Close();
                Invoke(new Action(() =>
                {
                    statusLabel.Text      = STATUS_BAR_DEFAULT;
                    uploadButton.Enabled  = true;
                    exploreButton.Enabled = true;
                    parseButton.Enabled   = true;
                    exportButton.Enabled  = true;
                    textBox2.Enabled      = true;
                    stopButton.Enabled    = false;
                    fromBox.Enabled       = true;
                    toBox.Enabled         = true;
                }));
                service.Dispose();
                browser.Dispose();
            }
        }