使用 Scrapy 抓取 JSON 响应

Posted

技术标签:

【中文标题】使用 Scrapy 抓取 JSON 响应【英文标题】:Scraping a JSON response with Scrapy 【发布时间】:2013-08-12 20:52:46 【问题描述】:

如何使用 Scrapy 抓取返回 JSON 的 Web 请求?例如,JSON 看起来像这样:


    "firstName": "John",
    "lastName": "Smith",
    "age": 25,
    "address": 
        "streetAddress": "21 2nd Street",
        "city": "New York",
        "state": "NY",
        "postalCode": "10021"
    ,
    "phoneNumber": [
        
            "type": "home",
            "number": "212 555-1234"
        ,
        
            "type": "fax",
            "number": "646 555-4567"
        
    ]

我希望抓取特定项目(例如上面的 namefax)并保存到 csv。

【问题讨论】:

【参考方案1】:

这与使用 Scrapy 的 htmlXPathSelector 进行 html 响应相同。唯一的区别是您应该使用json 模块来解析响应:

class MySpider(BaseSpider):
    ...


    def parse(self, response):
         jsonresponse = json.loads(response.text)

         item = MyItem()
         item["firstName"] = jsonresponse["firstName"]             

         return item

希望对您有所帮助。

【讨论】:

您可能希望使用json.loads(response.body_as_unicode()),因为加载需要strunicode 对象,而不是scrapy 响应。 伙计们,现在您已经解析了一个 json 响应。我将如何跟踪可能在 json 中的每个链接? @Cmag 你需要returnyield 一个Request,查看更多信息here。 使用ujson会更有效 response.text 优于 body_as_unicode(),见doc.scrapy.org/en/latest/topics/…【参考方案2】:

JSON 未加载的可能原因是它前后都有单引号。试试这个:

json.loads(response.body_as_unicode().replace("'", '"'))

【讨论】:

也可以是一个奇怪的json,例如用不必要的括号,然后使用:json.loads(response.body_as_unicode().strip('()')).【参考方案3】:

不需要使用json模块解析reponse对象。

class MySpider(BaseSpider):
...


def parse(self, response):
     jsonresponse = response.json()

     item = MyItem()
     item["firstName"] = jsonresponse.get("firstName", "")           

     return item

【讨论】:

我认为作为对已接受答案的评论会更好。 我需要“50 声望”才能发表评论,所以我不能。

以上是关于使用 Scrapy 抓取 JSON 响应的主要内容,如果未能解决你的问题,请参考以下文章

如何将抓取的数据从 Scrapy 以 csv 或 json 格式上传到 Amazon S3?

Scrapy:抓取返回数据格式为JSON的网站内容

解决Scrapy抓取中文网页保存为json文件时中文不显示而是显示unicode的问题

通过Scrapy抓取QQ空间

scrapy初探-斗鱼直播信息抓取

分布式爬虫:使用Scrapy抓取数据