Как да напиша робот? - уеб робот

Имах мисли да се опитвам да напиша обикновен робот, който може да обходи и да изготви списък с констатациите си за уебсайтовете и съдържанието на нашите НПО.

Някой има ли мисли как да направи това? Къде насочвате робота, за да започнете? Как изпраща своите констатации и продължава да пълзи? Как тя знае какво намира и т.н.

Отговори:

145 за отговор № 1

Вие ще преосмислите колелото, за да бъдете сигурни.

  • Списък на непридружени URL адреси - запълнете това с една или повече начални страници
  • Списък на посетените URL адреси - така че не обикаляте в кръгове
  • Набор от правила за URL адреси, които не ви интересуват - така че не индексирате целия интернет

Сложете ги в постоянна памет, така че да можете да спрете и да стартирате робота без да губите състояние.

Алгоритъмът е:

while(list of unvisited URLs is not empty) {
take URL from list
remove it from the unvisited list and add it to the visited list
fetch content
record whatever it is you want to about the content
if content is HTML {
parse out URLs from links
foreach URL {
if it matches your rules
and it"s not already in either the visited or unvisited list
add it to the unvisited list
}
}
}

29 за отговор № 2

Сложната част на робота е, ако искате да я увеличите до огромен брой уебсайтове / заявки. В тази ситуация ще трябва да се справите с някои проблеми като:

  • Невъзможност да се запази информацията в една база данни.

  • Няма достатъчно RAM за работа с огромни индекси

  • Многопоточна производителност и конкурентност

  • Капани на робота (безкраен цикъл, създаден чрез промяна на URL адреси, календари, идентификатори на сесии ...) и дублирано съдържание

  • Обхождане от повече от един компютър

  • Неправилни HTML кодове

  • Постоянни http грешки от сървъри

  • Бази данни без компресия, които правят необходимото ви пространство около 8x по-голямо.

  • Обхождане и приоритети.

  • Използвайте заявки със компресия (Deflate / gzip) (добре за всеки вид робот).

И някои важни неща

  • Уважавайте robots.txt

  • И един робот забави за всяка заявка да не задуши уеб сървъри.


8 за отговор № 3

Многопоточен Web Crawler

Ако искате да обхождате голям уебсайт, тогава виетрябва да напишете многократен робот. свързване, извличане и писане на индексирана информация във файлове / база данни - това са трите стъпки за обхождане, но ако използвате единична нишка, отколкото процесора и използването на мрежата ще се излива.

Многопоточен уеб-робот се нуждае от две структури за данни - linksVisited (това трябва да се реализира като hashmap или trai) и linksToBeVisited (това е опашка).

Web crawler използва BFS, за да пресече World Wide Web.

Алгоритъм на основния уеб-робот: -

  1. Добавете един или повече начални URL адреси към linksToBeVisited. Методът за добавяне на url към linksToBeVisited трябва да бъде синхронизиран.
  2. Поп елемента от linksToBeVisited и добавете това към linksVisited. Този поп метод за поп URL от linksToBeVisited трябва да бъде синхронизиран.
  3. Изтеглете страницата от интернет.
  4. Разбор на файла и добавяне на досега не посетената връзка, намираща се в страницата, към linksToBeVisited. URL адресът "s може да бъде филтриран, ако е необходимо. Потребителят може да даде набор от правила, за да филтрира кои URL адреси да бъдат сканирани.
  5. Необходимата информация, намерена на страницата, се записва в база данни или файл.
  6. повторете стъпки 2 до 5, докато опашката е linksToBeVisited empty.

    Ето кодов фрагмент за това как да синхронизирате нишките ...

     public void add(String site) {
    synchronized (this) {
    if (!linksVisited.contains(site)) {
    linksToBeVisited.add(site);
    }
    }
    }
    
    public String next() {
    if (linksToBeVisited.size() == 0) {
    return null;
    }
    synchronized (this) {
    // Need to check again if size has changed
    if (linksToBeVisited.size() > 0) {
    String s = linksToBeVisited.get(0);
    linksToBeVisited.remove(0);
    linksVisited.add(s);
    return s;
    }
    return null;
    }
    }
    


5 за отговор № 4

Ако сайтовете ви на НПО са сравнително големи или сложни (с динамични страници, които ефективно ще създадат „черна дупка“ като календар с връзка „на следващия ден“, ще бъдете по-добре да използвате истински уеб-робот Heritrix.

Ако сайтовете съдържат няколко броя страници, които можетеда се размине само с помощта на къдря или wget или своя собствена. Само не забравяйте дали започват да стават големи или започнете да правите скрипта си по-сложен, за да използвате истински робот или поне да погледнете неговия източник, за да видите какво правят и защо.

Някои проблеми (има още):

  • Черни дупки (както е описано)
  • Повторен опит (какво ще стане, ако получите 500?)
  • пренасочвания
  • Контрол на потока (иначе можете да бъдете тежест на сайтовете)
  • изпълнение на robots.txt

4 за отговор № 5

Пейджърите са опростени.

Можете да получите коренова страница чрез HTTP GET, да я анализирате, за да намерите URL адреси и да ги поставите на опашка, освен ако вече не са били анализирани (така че имате нужда от глобален запис на страници, които вече сте разбрали).

Можете да използвате заглавната част от типа на съдържанието, за да разберете какъв е типът на съдържанието и да ограничите своя робот само да анализира типовете HTML.

Можете да премахнете HTML таговете, за да получите обикновенататекст, който можете да направите за анализ на текст (за да получите тагове и т.н., месото на страницата). Можете дори да направите това на alt / заглавието тагове за изображения, ако имаш, че напреднали.

А във фонов режим можете да имате пул от нишки, които да ядат URL адреси от опашката и да правят същото. Разбира се, искате да ограничите броя на нишките.


4 за отговор № 6

Уикипедия има добра статия уеб търсачки, обхващащи много от алгоритмите и съображенията.

Въпреки това, аз няма да си правя труда да пиша собствения си робот. Това е много работа, и тъй като имате нужда само от "обикновен робот", мисля, че всичко, от което наистина се нуждаете, е безжичен робот, Има много свободни и открити роботи, които най-вероятно ще направят всичко, от което се нуждаете, с много малко работа от ваша страна.


2 за отговор № 7

Можете да направите списък с думи и да направите нишка за всяка дума, която търсите в Google.
След това всеки конец ще създаде нов конец за всяка връзка, която намира в страницата.
Всяка нишка трябва да напише това, което намира в базата данни. Когато всяка нишка приключи четенето на страницата, тя се прекратява.
И там имате много голяма база данни от връзки във вашата база данни.


1 за отговор № 8

Използвам отворения сървър за търсене за вътрешното ми търсене в компанията си, опитайте следното: http://open-search-server.com също така е отворен.


0 за отговор № 9

Използвайте wget, направете рекурсивен web suck, който ще изхвърли всички файлове на вашия твърд диск, след това напишете друг скрипт, за да прегледате всички изтеглени файлове и ги анализирайте.

Edit: или може би къдря вместо wget, но аз не съм запознат с къдря, не знам дали прави рекурсивни файлове като wget.


0 за отговор № 10

Направих обикновен уеб робот, използващ реактивно разширение в .net.

https://github.com/Misterhex/WebCrawler

public class Crawler
{
class ReceivingCrawledUri : ObservableBase<Uri>
{
public int _numberOfLinksLeft = 0;

private ReplaySubject<Uri> _subject = new ReplaySubject<Uri>();
private Uri _rootUri;
private IEnumerable<IUriFilter> _filters;

public ReceivingCrawledUri(Uri uri)
: this(uri, Enumerable.Empty<IUriFilter>().ToArray())
{ }

public ReceivingCrawledUri(Uri uri, params IUriFilter[] filters)
{
_filters = filters;

CrawlAsync(uri).Start();
}

protected override IDisposable SubscribeCore(IObserver<Uri> observer)
{
return _subject.Subscribe(observer);
}

private async Task CrawlAsync(Uri uri)
{
using (HttpClient client = new HttpClient() { Timeout = TimeSpan.FromMinutes(1) })
{
IEnumerable<Uri> result = new List<Uri>();

try
{
string html = await client.GetStringAsync(uri);
result = CQ.Create(html)["a"].Select(i => i.Attributes["href"]).SafeSelect(i => new Uri(i));
result = Filter(result, _filters.ToArray());

result.ToList().ForEach(async i =>
{
Interlocked.Increment(ref _numberOfLinksLeft);
_subject.OnNext(i);
await CrawlAsync(i);
});
}
catch
{ }

if (Interlocked.Decrement(ref _numberOfLinksLeft) == 0)
_subject.OnCompleted();
}
}

private static List<Uri> Filter(IEnumerable<Uri> uris, params IUriFilter[] filters)
{
var filtered = uris.ToList();
foreach (var filter in filters.ToList())
{
filtered = filter.Filter(filtered);
}
return filtered;
}
}

public IObservable<Uri> Crawl(Uri uri)
{
return new ReceivingCrawledUri(uri, new ExcludeRootUriFilter(uri), new ExternalUriFilter(uri), new AlreadyVisitedUriFilter());
}

public IObservable<Uri> Crawl(Uri uri, params IUriFilter[] filters)
{
return new ReceivingCrawledUri(uri, filters);
}
}

и можете да го използвате, както следва:

Crawler crawler = new Crawler();
IObservable observable = crawler.Crawl(new Uri("http://www.codinghorror.com/"));
observable.Subscribe(onNext: Console.WriteLine,
onCompleted: () => Console.WriteLine("Crawling completed"));