2016-12-27 7 views
1

Scrapyを使用してスクレイパーを作成する途中ですが、その非同期動作が問題を引き起こす可能性があることを心配しています。Scrapyを使用して2つのサイトからアイテムを繰り返し取得する

私はxをそれぞれ得ているいくつかのリンクaからのページから始めます。これらはxが保存(ダウンロード)されます。次に私は別のページbに行きます。私はaリンクから入手した情報を使用します(それはすべてが一定です)。yを選択してダウンロードしてください。
次に私は "xyをペアにして、どのように重要ではないかということは、xyの両方が存在する(ダウンロードされる)ことです。
開始ページ(start_urls)が処理されたと見なし、ページをめくるためのリンクを取得します(ページ1にあり、ページ2に移動しています)。プロセスは最初から。

コードは、おおよそ次のようになります。

# ..imports, class etc. 

start_url = ['bla'] 
start_url_buddy = ['bli'] 


def parse(self, response): 

    urls = response.xpath(...) 
    for url in urls: 
     yield scrapy.Request(url, callback=self.parse_child) 

    yield scrapy.Request(start_url_buddy, callback=self.parse_buddy) 

    pair_function(self.info) 

    # Finished processing start page. Now turning the page. 
    # could do smth like this to get next page: 
    nextpage_url = response.xpath([email protected]) 
    yield scrapy.Request(nextpage_url) 

    # or maybe something like this? 
    start_urls.append(response.xpath([email protected])) 

# links `a` 
def parse_child(self, response): 

    # info for processing link `b` 
    self.info = response.xpath(...) 

    # Download link 
    x = response.xpath(...) 
    # urlopen etc. write x to file in central dir 

# link `b` 
def parse_buddy(self, response): 

    # Download link 
    y = response.xpath(...self.info...) 
    # urlopen etc. write y to file in central dir 

私は(私は、マージ機能のATMをいじる取得しています、まだ一部のページめくりに得と意図したとおりにそれが機能するかどうか心配していませんxyは1ページで正常に動作します)。私はの前で、「ページをめくる」(解析機能が再度あるはずです)の前にある限り、xyの順番を気にしません。

私はthisのような他の2つの質問を見ましたが、私はそれらから明確な答えを得ることができませんでした。私の基本的な問題は、非同期性がどのくらい正確に実装されているかについてはわかりません(ドキュメントで説明されていないようです)。

EDIT:私が怖がっていることを明らかにするには、前のものが終了する前にyield scrapy.Request(nextpage_url)が呼び出されるということです。私は今、すべてが完了した後でstart_urlsに追加しただけで、それに対して安全なガードができると考えています(ロジックでは、追加されたURLでparse関数が呼び出されるはずです)

+0

これを実行する前に、ページは順番に要求されますが、応答は非同期で受信されます。あなたが求めているのはこれですか? – Tyler

+0

OPを編集して、私が恐れていることをより明確にします。 – Nimitz14

答えて

2

scrapyは、すべてのリクエストを処理しているとしてあなたは、要求が終了したときに知ることができなくなりますが、それは次の保留中の要求を処理する前に応答を返すように要求されたサーバを待ちません。

非同期呼び出しについては、「いつ」終了するのかわからないのですが、「どこで」、それがコールバックメソッドなのかを知っています。例えば、次のようにして、

def callback_method_1(self, response): 
    # working with response 1 
    yield Request(url2, callback=self.callback_method_2) 

def callback_method_2(self, response): 
    # working with response 2, after response 1 
    yield Request(url3, callback=self.callback_method_3) 

def callback_method_3(self, response): 
    # working with response 3, after response 2 
    yield myfinalitem 

この例では、最初の要求がurl2要求の前に実行されたことを確認しています。これはurl3より前です。ご覧のとおり、これらのリクエストがいつ行われたかは正確に分かりませんが、「どこで」知っていますか。

コールバック間で通信する方法は、metaリクエスト引数を使用していることにも注意してください。

+0

最初の 'Requests'がどのような順序で呼び出されているかは問題ではありません(' urls'のurl 'url')。私にとって重要なのは、最後のものが 'yield scrapy.Request(nextpage_url)'と呼ばれる前にすべてが終了していることだけです。 – Nimitz14

+1

私は唯一の治療法があなたに説明した。 ( 'parse'メソッドのように)あるメソッドから複数のリクエストを送信すると、それらのリクエストはすべて非同期で処理されているので、コードのどの行にあっても問題はありません。コールバックの考え。 – eLRuLL

+0

ああ、申し訳ありません、ありがとうございます。だから私は別の機能に入れてリクエストを "隠す"ことができますか?私が3つの 'yield'リクエストを持つ' parse'関数を持っていて、最後のものを別の関数の中に入れたら、最初の2つが最後のものの前に処理されるでしょうか? – Nimitz14

関連する問題