2012-12-28 15 views

Odpowiedz

19

Ok, więc dokumentacja na http://doc.scrapy.org/en/latest/topics/extensions.html mówi, że

The main entry point for a Scrapy extension (this also includes middlewares and pipelines) is the from_crawler class method which receives a Crawler instance which is the main object controlling the Scrapy crawler. Through that object you can access settings, signals, stats, and also control the crawler behaviour, if your extension needs to such thing.

Więc można mieć funkcję, aby uzyskać ustawienia.

@classmethod 
def from_crawler(cls, crawler): 
    settings = crawler.settings 
    my_setting = settings.get("MY_SETTING") 
    return cls(my_setting) 

Silnik gąsienicowy następnie wywołuje funkcję init tego gazociągu z my_setting, tak:

def __init__(self, my_setting): 
    self.my_setting = my_setting 

i innych funkcji można uzyskać do niego dostęp z self.my_setting, jak oczekiwano.

Alternatywnie, w funkcji from_crawler() można przekazać obiekt crawler.settings do __init__(), a następnie ustawienia dostępu z rurociągu, ile potrzeba, a nie ciągnąc je wszystkie w konstruktorze.

+0

To brzmi strasznie skomplikowane. Czy nie ma prostszego sposobu na to, czy może lepszego wyjaśnienia? Czy nie możesz użyć 'from scrapy.settings import Settings '? – not2qubit

+1

@ user1147688 Użyłbym tej metody, ponieważ jest ona zgodna z wewnętrznym API opartym na wtrysku zależności od scrapy. Twoja sugestia może zadziałać, ale wygląda na to, że nie ma gwarancji, że będzie ona obowiązywać w przyszłości, ponieważ wewnętrzne interfejsy API mogą być przenoszone. – deceze

+0

@avaleske, działa to niesamowicie, ale czy wiesz, w jaki sposób możemy użyć tego do ustawienia? Na przykład, w innej funkcji, powiedz, że chciałem zmienić jedną z wartości ustawień, takich jak 'download_delay'. Czy możemy to zrobić? – thefoxrocks

18

Sposób dostępu do ustawień Scrapy (zgodnie z definicją w settings.py) z poziomu your_spider.py jest prosty. Wszystkie inne odpowiedzi są zbyt skomplikowane. Powodem tego jest bardzo słaba konserwacja dokumentacji Scrapy, w połączeniu z wieloma nowymi aktualizacjami & zmian. Ani w "Ustawieniach" dokumentacji "How to access settings", ani w "Settings API" nie zadali sobie trudu nadając praktyczny przykład. Oto przykład, w jaki sposób uzyskać bieżący ciąg znaków USER_AGENT.

Wystarczy dodać następujące linie do your_spider.py:

# To get your settings from (settings.py): 
from scrapy.utils.project import get_project_settings 
... 
class YourSpider(BaseSpider): 
    ... 
    def parse(self, response): 
     ... 
     settings = get_project_settings() 
     print "Your USER_AGENT is:\n%s" % (settings.get('USER_AGENT')) 
     ... 

Jak widać, nie ma potrzeby korzystania @classmethod lub ponowne zdefiniowanie from_crawler() lub __init__() funkcje. Mam nadzieję że to pomoże.

PS. Nadal nie wiem, dlaczego używanie from scrapy.settings import Settings nie działa w ten sam sposób, ponieważ byłby to bardziej oczywisty wybór importu?

+0

Mimo że dokumentacja sugeruje zastosowaną metodę @avaleske, nadal wolę ten sposób, ponieważ działa i jest szybszy do zrozumienia. –

+3

Ta metoda ** nie ** rozpoznała ustawień, które zostały [przesłonięte z wiersza poleceń] (http://doc.scrapy.org/en/0.24/topics/settings.html#command-line-options). Użyj odpowiedzi @ avaleske, jeśli chcesz korzystać z tej funkcji. –

13

Prawidłowa odpowiedź: zależy od miejsca, w którym chcesz uzyskać dostęp do ustawień.

avaleske odpowiedział tak, jakbyś chciał uzyskać dostęp do ustawień poza linią process_item, ale jest bardzo prawdopodobne, że właśnie tam będziesz chciał ustawić i dlatego jest o wiele łatwiejszy sposób, gdy sama instancja Spidera zostanie przekazana jako argument.

class PipelineX(object): 

    def process_item(self, item, spider): 
     wanted_setting = spider.settings.get('WANTED_SETTING') 
+1

Świetna odpowiedź. W moim projekcie bardziej logiczne było umieszczenie logiki w metodzie 'open_spider', ponieważ używam tylko tej wartości, kiedy pająk ładuje się po raz pierwszy. –

2

struktura projektu jest dość płaski, dlaczego nie:

# pipeline.py 
from myproject import settings 
Powiązane problemy