2013-07-20 12 views
6

Il mio raschietto funziona correttamente quando lo eseguo dalla riga di comando, ma quando provo a eseguirlo da uno script python (con il metodo indicato here usando Twisted) non emette i due file CSV che normalmente fa. Ho una pipeline che crea e popola questi file, uno dei quali usa CsvItemExporter() e l'altro usando writeCsvFile(). Ecco il codice:Running scrapy from inside Python script - CSV exporter non funziona

class CsvExportPipeline(object): 

    def __init__(self): 
     self.files = {} 

    @classmethod 
    def from_crawler(cls, crawler): 
     pipeline = cls() 
     crawler.signals.connect(pipeline.spider_opened, signals.spider_opened) 
     crawler.signals.connect(pipeline.spider_closed, signals.spider_closed) 
     return pipeline 

    def spider_opened(self, spider): 
     nodes = open('%s_nodes.csv' % spider.name, 'w+b') 
     self.files[spider] = nodes 
     self.exporter1 = CsvItemExporter(nodes, fields_to_export=['url','name','screenshot']) 
     self.exporter1.start_exporting() 

     self.edges = [] 
     self.edges.append(['Source','Target','Type','ID','Label','Weight']) 
     self.num = 1 

    def spider_closed(self, spider): 
     self.exporter1.finish_exporting() 
     file = self.files.pop(spider) 
     file.close() 

     writeCsvFile(getcwd()+r'\edges.csv', self.edges) 

    def process_item(self, item, spider): 
     self.exporter1.export_item(item) 

     for url in item['links']: 
      self.edges.append([item['url'],url,'Directed',self.num,'',1]) 
      self.num += 1 
     return item 

Qui è la mia struttura dei file:

SiteCrawler/  # the CSVs are normally created in this folder 
    runspider.py # this is the script that runs the scraper 
    scrapy.cfg 
    SiteCrawler/ 
     __init__.py 
     items.py 
     pipelines.py 
     screenshooter.py 
     settings.py 
     spiders/ 
      __init__.py 
      myfuncs.py 
      sitecrawler_spider.py 

Il raschietto sembra funzionare normalmente in tutti gli altri modi. L'output alla fine della riga di comando indica che il numero previsto di pagine è stato scansionato e che sembra che lo spider sia terminato normalmente. Non ricevo alcun messaggio di errore.

---- EDIT: ----

Inserimento dichiarazioni di stampa e gli errori di sintassi nella pipeline non ha alcun effetto, così sembra che la pipeline viene ignorato. Perché potrebbe essere?

ecco il codice per lo script che viene eseguito il raschietto (runspider.py):

from twisted.internet import reactor 

from scrapy import log, signals 
from scrapy.crawler import Crawler 
from scrapy.settings import Settings 
from scrapy.xlib.pydispatch import dispatcher 
import logging 

from SiteCrawler.spiders.sitecrawler_spider import MySpider 

def stop_reactor(): 
    reactor.stop() 

dispatcher.connect(stop_reactor, signal=signals.spider_closed) 
spider = MySpider() 
crawler = Crawler(Settings()) 
crawler.configure() 
crawler.crawl(spider) 
crawler.start() 
log.start(loglevel=logging.DEBUG) 
log.msg('Running reactor...') 
reactor.run() # the script will block here until the spider is closed 
log.msg('Reactor stopped.') 
+1

I file potrebbero essere scritti da qualche altra parte? puoi controllare i percorsi dei file di uscita o utilizzare percorsi di file assoluti? –

+0

@pault. Buon punto Ora l'ho provato usando os.path.dirname (__ file__), getcwd() e il percorso esatto del file digitato. Purtroppo, questi non hanno fatto alcuna differenza. – jkdune

+0

Ho provato ad aggiungere istruzioni di stampa per mostrare quali output getcwd() e os.path.dirname (file), ma non sembrano eseguire. Significa che la pipeline viene ignorata? O sta eseguendo questo all'interno del reattore che interferisce con la stampa? – jkdune

risposta

1

Sostituire "da scrapy.settings import Settings" con "from scrapy.utils.project import get_project_settings as Settings" ha risolto il problema.

La soluzione è stata trovata here. Non è stata fornita alcuna spiegazione della soluzione.

alecxe ha fornito an example di come eseguire Scrapy da uno script Python.

EDIT:

Avendo letto attraverso il post di alecxe più in dettaglio, ora posso vedere la differenza tra "da scrapy.settings importare le impostazioni" e "dal scrapy.utils.project get_project_settings importazione Impostazioni". Quest'ultimo consente di utilizzare il file delle impostazioni del progetto, al contrario di un file di impostazioni defualt. Leggi il post di alecxe (collegato a sopra) per maggiori dettagli.

0

Nel mio progetto che io chiamo il codice di Scrapy all'interno di un altro script python usando os.system

import os 
os.chdir('/home/admin/source/scrapy_test') 
command = "scrapy crawl test_spider -s FEED_URI='file:///home/admin/scrapy/data.csv' -s LOG_FILE='/home/admin/scrapy/scrapy_test.log'" 
return_code = os.system(command) 
print 'done'