scrapy.Request.meta傳遞參數出現重復問題的解決方案


  一旦Spider的爬取的深度比較深時,數據的提取基本上是貫穿每一層的,為了將數據一層一層傳遞下去,我們需要將上一層提取的數據傳遞到下一層,供下一層使用,這時我們就需要使用的scrapy.Request的meta參數,其是一個字典。在傳遞不變數據時,不需要擔心,但是我們傳遞的是一個Item類型或字典,這兩者都屬於可變類型,恰好又與scrapy的異步機制發生了碰撞,當我們將一個字典(或者Item)裝進meta里面時,Item就會從Spider經過Engine最終到Pipeline,如果在這期間,Item被修改了,那么被Pipeline過濾、加工、存儲的Item也會相應的改變,簡而言之就是淺拷貝的問題,解決方法深拷貝。

  所以最終建議使用copy.deepcopy函數進行深拷貝

def parse(self, response):
        province_list = response.xpath("//div[@class='city_province']")
        for province in province_list:
            province_name = province.xpath("./div/text()").get()
            city_list = province.xpath("./ul/li/a")
            for city in city_list:
                item = {}
                city_name = city.xpath("./text()").get()
                city_url = city.xpath("./@href").get()
                # 鏈接分為兩類:沒有二手房的鏈接和有二手房的鏈接
                if "fang" in city_url:
                    continue
                # print(province_name, city_name, city_url)
                # 將所有城市的鏈接轉化為二手房的鏈接
                city_esf_url = city_url + "ershoufang/co32/"
                item["province"] = province_name
                item["city"] = city_name
                yield scrapy.Request(url=city_esf_url, callback=self.parse_city, meta={"item": copy.deepcopy(item)})

  另外建議,進行深拷貝的位置也是有講究的,必須在meta里進行深拷貝,否則也會出現重復。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM