Crawler

Stellt hier eure Projekte vor.
Internetseiten, Skripte, und alles andere bzgl. Python.
Antworten
nemomuk
User
Beiträge: 862
Registriert: Dienstag 6. November 2007, 21:49

Hallo,

da ich vor kurzer Zeit selbst einen Crawler gebraucht habe, der eine relativ große Anzahl von Seiten druchcrawlen musste, habe ich mir eine kleine Library geschrieben. Vllt. braucht jemand (außer mir) sowas in der Art in Zukunft. Man kann eigentlich relativ simpel seinen eigenen Crawler erstellen und muss sich nur um die Parser und restlichen Algorithmen kümmern (was wird wann geladen). Das Crawlen wird von der Engine übernommen, heißt aber auch, dass sich die Engine um nichts anderes kümmert als den Crawl-Vorgang. Hier mal ein kleines Beispiel:

Code: Alles auswählen

# -*- coding: utf-8 -*-
from crawler import Crawler
from example_database import session, HostModel, PathModel
from sqlalchemy.exceptions import IntegrityError
import re
import urlparse
import httplib
from collections import defaultdict


REGEX_HREF = re.compile("<a .*href=[\"\"](.*?)[\"\"].*>.*?</a>", re.I)

def custom_parser(url, headers, document):
    print url
    hostname = urlparse.urlsplit(url).hostname
    hrefs = re.findall(REGEX_HREF, document)
    found_urls = defaultdict(list)
    for href in hrefs:
        href = urlparse.urlsplit(href)
        found_hostname = href.hostname or hostname
        found_path = (href.path + href.query) or '/'
        if href.scheme == 'http':
            found_urls[found_hostname].append(found_path)
    for found_hostname,found_paths in found_urls.iteritems():
        try:
            Host = HostModel(name=found_hostname)
            session.commit()
        except IntegrityError:
            session.rollback()
        for found_path in set(found_paths):
            try:
                PathModel(hostname=found_hostname, path=found_path)
                session.commit()
            except IntegrityError:
                session.rollback()
                
def custom_feeder():
    paths = PathModel.query.filter_by(visited=False).limit(40).all()
    data = []
    for path in paths:
        path.visited = True
        url = urlparse.urlunsplit(['http', path.hostname, path.path, '', ''])
        data.append(url)
    session.commit()
    return data
                
def main():
    crawler = Crawler()
    crawler.parser.set(custom_parser, httplib.OK)
    crawler.feeder.set(custom_feeder)
    crawler.downloader.amount = 20
    crawler.downloader.max_size = 1024**2
    crawler.download('http://www.spiegel.de/')
    crawler.start()
    
if __name__ == '__main__':
    main()
Hier der Programm-Code: http://paste.pocoo.org/show/130270/

Ihr dürft auch gerne Anmerkungen und Verbesserungsvorschläge machen. Über den Sinn der Anwendung muss nicht diskutiert werden, ich habe es benötigt und jetzt einfach zur allgemeinen Verfügung gestellt.[/code]
Antworten