Python 刮痧:可以';t爬行应用商店评论页面

Python 刮痧:可以';t爬行应用商店评论页面,python,ios,web-scraping,scrapy,app-store,Python,Ios,Web Scraping,Scrapy,App Store,大家好,我在从app store获取此页面数据时遇到了一些问题: 我想首先检索一个字符串,显示用户对应用程序的评分。它们位于一个带有class=“we star rating ember view we-customer-review\uu rating we star rating--large”的图形标记内,是属性@aria label的名称 这是我的密码: from scrapy import Selector import requests html = requests.get(

大家好,我在从app store获取此页面数据时遇到了一些问题:

我想首先检索一个字符串,显示用户对应用程序的评分。它们位于一个带有class=“we star rating ember view we-customer-review\uu rating we star rating--large”的图形标记内,是属性@aria label的名称

这是我的密码:

from scrapy import Selector
import requests

html = requests.get('https://apps.apple.com/us/app/mathy-cool-math-learner-games/id1476596747#see-all/reviews').content

sel = Selector(text = html)

sel.xpath('//figure[@class="we-star-rating ember-view we-customer-review__rating we-star-rating--large"]/@aria-label').extract()

但它只返回前3个匹配项:

['5 out of 5', '5 out of 5', '5 out of 5']
我想要的是从该页面的所有评论中检索所有可用的评分

有人能给我一个线索吗?

这个问题 前三个评论是作为HTML的一部分加载的,但其余的是通过javascript加载的。这就是为什么你只能得到前三个结果

我不完全确定这是否是您使用scrapy的全部代码。我很想知道你为什么要选那一部分

因此,使用javascript进行设计是现代网站抓取的一个重要组成部分。我不完全确定你是否主要是在用“刮痧”来拉网。不过,有几个选项可以使用scrapy处理javascript

关于动态Web抓取的信息 首先要知道,现在的网站在动态地获取信息,使用javascript调用HTTP请求,称为AJAX请求(异步javascript和XHTML)。这会向API/服务器发出post或get HTTP请求,HTTP响应会返回信息。在本例中,他们已将3个结果预加载到HTML中,但在使用javascript加载页面时要求查看其余结果

一般来说,有两种方法可以处理面向javascript的网站

  • 重新设计HTTP请求-这是获取所需数据的最有效方法。您希望模拟javascript正在调用的这些HTTP请求。如果您可以这样做,并且有时需要发布标题、参数和cookie,那么您就可以获得所需的数据
  • 使用某种形式的浏览器自动化。硒是首选包装,尽管最初从未打算以这种方式使用。如果使用更大的数据集,速度慢、效率低且脆弱
  • 解决方案 对于您的特定网站,您可以重新设计HTTP请求以获取所需信息。这是理想的情况

    但我怎么知道的?在chrome中可以做的一件事就是关闭javascript。您必须检查页面并进入设置(单击页面右侧的三个点->更多工具->设置)。在不使用javascript的情况下刷新页面。你会看到只有三篇评论要看

    使用ChromeDev工具了解正在发生的事情非常有用。如果在右键单击并检查页面时转到“网络”选项卡,您将看到服务器发出的所有请求和响应。转到XHR选项卡,您将找到包含所需数据的请求。这里有一堆请求和响应

    看到下面的图片,我已经检查了页面,进入网络并刷新了页面。这将记录浏览器请求和响应的活动

    您可以看到大约有6个请求,5个GET请求和一个POST请求。如果单击每个请求,您将在右侧看到一个弹出框,其中包含请求数据、预览和响应

    在这里,我单击了第一个请求,我单击了预览,您可以看到,如果您单击,就会看到一些评论

    我可以在HTTP请求中看到该数据的偏移量为10,这意味着它将捕获接下来的10个请求

    所以我要改变这个偏移量,看看我是否能得到前10个,然后是第二个10个(这页上有20个评论)

    无需手动输入参数和标题等。。。您可以将请求复制到卷曲中。然后可以使用类似于
    curl.trillworks.com
    的站点将其转换为一种不错的python格式

    现在,查看预览数据是值得的,因为您必须使用请求来处理这些数据。您将得到一个JSON对象,您可以从HTTP get请求的接受部分看出这一点,即
    application/JSON

    把这个请求复制到curl.trillworks.com。我们有下面的例子

    编码示例 我在上面提到过,有时需要标题和参数。您可以在这里使用requestget方法,看看是什么获取了数据。在本例中,您需要参数和标题。情况并非总是如此,因此您应该始终执行一个简单的
    请求。get()
    ,而不执行任何操作,然后构建它。
    json()
    方法将json对象格式化为python字典,以便我们可以轻松访问数据

    现在,当我说查看预览时,会为我们提供访问数据所需的键和值。有时数据可以嵌套得很深。在这种情况下,它不是,所以我们现在考虑在这个字典上循环以获得我们想要的所有数据。我们必须发出两个HTTP请求,一个偏移量为0,另一个偏移量为10,以获得完整的20星评级

    最后一个代码示例 输出 代码解释
  • 我们使用发出请求所需的标题(我设法在没有标题的情况下获取数据,但在尝试获取所有数据时,似乎需要标题,但您可以使用它)

  • 我们正在循环所需的参数,在这种情况下,我们希望偏移量为0,10。所以我们使用
    范围(0,20,10)
    来得到它。对于每个参数,我们使用头和这些特定参数发出一个HTTPGET请求

  • 我们使用
    response.json()

  • 如果您输出这个,我们可以看到很多数据,我们需要在
    data
    键中,如下所示。如果您打印此文件,您将得到以下输出

    data=response.json()['data'] 打印(数据)
    import requests
    
    headers = {
        'Accept': 'application/json',
        'Referer': 'https://apps.apple.com/us/app/mathy-cool-math-learner-games/id1476596747',
        'Authorization': 'Bearer eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IldlYlBsYXlLaWQifQ.eyJpc3MiOiJBTVBXZWJQbGF5IiwiaWF0IjoxNTk2NTc1NTY4LCJleHAiOjE2MTIxMjc1Njh9.jnEuBNEVWhKGqI10W6dfhJFtYJtd74Nbu1NueZrPgYjU2K34LwXPQClcus8S9Jit5ayK5MOr0bIpcDx821RI4Q',
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36',
        'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
    }
    
    params = (
        ('l', 'en-US'),
        ('offset', '1'),
        ('platform', 'web'),
        ('additionalPlatforms', 'appletv,ipad,iphone,mac'),
    )
    
    response = requests.get('https://amp-api.apps.apple.com/v1/catalog/us/apps/1476596747/reviews', headers=headers params=params)
    response.json()
    
    import requests
    
    headers = {
        'Accept': 'application/json',
        'Referer': 'https://apps.apple.com/us/app/mathy-cool-math-learner-games/id1476596747',
        'Authorization': 'Bearer eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IldlYlBsYXlLaWQifQ.eyJpc3MiOiJBTVBXZWJQbGF5IiwiaWF0IjoxNTk2NTc1NTY4LCJleHAiOjE2MTIxMjc1Njh9.jnEuBNEVWhKGqI10W6dfhJFtYJtd74Nbu1NueZrPgYjU2K34LwXPQClcus8S9Jit5ayK5MOr0bIpcDx821RI4Q',
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36',
        'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
    }
    for i in range(0,20,10):
        
        params = (
            ('l', 'en-US'),
            ('offset', f'{i}'),
            ('platform', 'web'),
            ('additionalPlatforms', 'appletv,ipad,iphone,mac'),
        )
        response = requests.get('https://amp-api.apps.apple.com/v1/catalog/us/apps/1476596747/reviews', params=params)
        data =  response.json()['data']
        for a in data:
            print(a['attributes']['rating'])
    
    5
    5
    5
    5
    5
    ...