2016-06-16 6 views
3

私はPython、Scrapy、およびこのボードにはかなり新しいので、私の問題を説明しようとしています。Scrap Crawledページですが、0個のアイテムを削った

私の目標は、scrapyの助けを借りて特定の日付(たとえば、事前定義されたstart_urlを参照)のbooking.comでベルリンの利用可能なすべてのホテルの名前(および場合によっては価格)を収集することです。

私は、重要な部分があると思います:

  1. 私は最後まで、すべての次のページをページ分割します。
  2. それぞれのページで、私はすべてのホテルの名前を集めたいと思います。名前はそれぞれ保存する必要があります。

私のコードで「scrapy runspider bookingspider.py -o items.csv -t csv」を実行すると、ターミナルから使用可能なすべてのページがクロールされているように見えますが、最後に空白になりますitems.csv。

端末が次のURLがクロールされている(たとえば、[...] offset = 15、[...] offset = 30など)ように見えるので、手順1はうまくいくようです。したがって、私の問題はステップ2であると思います。 ステップ2では、各ホテルの情報が別々に格納され、ループの基礎となるコンテナまたはブロックを定義する必要があります。 私は "div class =" sr_item_content sr_item_content_slider_wrapper ""を選びました。すべてのホテルのブロックにこの要素が上位レベルにあるためですが、この部分については本当にわかりません。たぶん、より高いレベルの を考えなければならないかもしれません(ただし、ホテルのブロックでは同じではないので、どの要素を取るべきですか?)。 とにかく、残りのXPathが要素に含まれていることがわかりました。これにはホテル名が含まれています。

私は同様の設定(別のウェブサイトでも)を持つ2つのチュートリアルに続きましたが、何とかここでは機能しません。

多分あなたはアイデアを持っている、すべての助けは非常に感謝しています。ありがとうございました!

from scrapy.spiders import CrawlSpider 
from scrapy.selector import Selector 
from scrapy.item import Item, Field 
from scrapy.http.request import Request 

class HotelItem(Item): 
    title = Field() 
    price = Field() 

class BookingCrawler(CrawlSpider): 
    name = 'booking_crawler' 
    allowed_domains = ['booking.com'] 
    start_urls = ['http://www.booking.com/searchresults.html?checkin_monthday=25;checkin_year_month=2016-10;checkout_monthday=26;checkout_year_month=2016-10;class_interval=1;dest_id=-1746443;dest_type=city;offset=0;sb_travel_purpose=leisure;si=ai%2Cco%2Cci%2Cre%2Cdi;src=index;ss=Berlin'] 
    custom_settings = { 
     'BOT_NAME': 'booking-scraper', 
     } 

    def parse(self, response): 
     s = Selector(response) 
     index_pages = s.xpath('//div[@class="results-paging"]/a/@href').extract() 
     if index_pages: 
      for page in index_pages: 
       yield Request(response.urljoin(page), self.parse) 

     hotels = s.xpath('//div[@class="sr_item_content sr_item_content_slider_wrapper"]') 
     items = [] 
     for hotel in hotels: 
      item = HotelItem() 
      item['title'] = hotel.xpath('div[1]/div[1]/h3/a/span/text()').extract()[0] 
      item['price'] = hotel.xpath('//div[@class="sr-prc--num sr-prc--final"]/text()').extract()[0] 
      items.append(item) 

     for item in items: 
      yield item 

答えて

-1

は、私はこの問題は、この行にXPathとかもしれないと思う:

//div[contains(@class, 'sr_item_content') and contains(@class, 'sr_item_content_slider_wrapper')]:あなたはの線に沿ってより多くの何かを定義する必要があるように見えるthis SO questionから

hotels = s.xpath('//div[@class="sr_item_content sr_item_content_slider_wrapper"]')

さらにデバッグを手助けするために、t彼の内容はindex_pagesです。あなたがそのレベルで期待していることを確実に返しているかどうかを最初に確認してください。

また、Xpathの作成に役立つXpath Visualiser(質問にも記載されています)をチェックしてください。

+1

ありがとうございます。私はhotels = s.xpath( '// div [contains(@class、 "sr_item_new")]) "をそれぞれのホテルブロックを導入して使用します。これは、端末が各クロールされたページについてより多くを示すように役立ちますが、クロールされたページごとに「IndexError:リストインデックスが範囲外です」を返します。アイデアはありますか? Btw、XPath Visualizerを試しましたが、何度も何度もクラッシュするので予約XMLを処理できないようです。 –

+0

@MaikDrop心配する必要はありません! 'item ['title'] = hotel.xpath( 'div [1]/div [1]/h3/a/span/text()')の行に配列があると思います。[価格]] = hotel.xpath( '// div [@ class = "sr-prc-num sr-prc-final"]/text()')。extract()[0] )[0] 'は空です。これらの行のコードも更新しましたか?この記事があなたの問題を解決した場合は、それを答えとしてマークして、次の問題の新しい質問を作成することができます – Bassie

+0

はい、私はそうでした、例えば 'item ['title'] = hotel.xpath( 'div [2 ]/div [1]/div [1]/h3/a/span/text() ')。extract()[0] '。それでも、それは動作しません。基本的に私は同じ問題を抱えていますが、クロールされたページごとにエラーが発生して0個のアイテムが収集されます。私の間違いは何ですか?ホテルのパスに基づいて、残りのXPathを要素に使用します。ありがとうございました。 –

関連する問題