【问题标题】:How to specify parameters on a Request using scrapy如何使用scrapy在请求上指定参数
【发布时间】:2015-11-17 00:32:57
【问题描述】:

如何将参数传递给这样的 url 上的请求:

site.com/search/?action=search&description=My Search here&e_author=

如何将参数放在 Spider 请求的结构上,例如以下示例:

req = Request(url="site.com/",parameters={x=1,y=2,z=3})

【问题讨论】:

  • 你可能想看看furl

标签: python web-crawler scrapy scrapy-spider


【解决方案1】:

在 URL 中传递你的 GET 参数:

return Request(url="https://yoursite.com/search/?action=search&description=MySearchhere&e_author=")

您可能应该在字典中定义您的参数,然后 "urlencode" 它:

from urllib.parse import urlencode

params = { 
    "action": "search",
    "description": "My search here",
    "e_author": ""
}
url = "https://yoursite.com/search/?" + urlencode(params)

return Request(url=url)

【讨论】:

  • 对不起,我不明白如何把它放在scrapy结构上
【解决方案2】:

您必须使用您拥有的任何参数自己制作 url。

Python 3 或更高版本

import urllib
params = {
    'key': self.access_key,
    'part': 'snippet,replies',
    'videoId': self.video_id,
    'maxResults': 100
}
url = f'https://www.googleapis.com/youtube/v3/commentThreads/?{urllib.parse.urlencode(params)}'
request = scrapy.Request(url, callback=self.parse)
yield request

Python 3+ 示例
在这里,我正在尝试使用官方 youtube api 获取一些 youtube 视频的所有评论。评论将采用分页格式。所以看看我是如何从 params 构造 url 来调用它的。

import scrapy
import urllib
import json
import datetime
from youtube_scrapy.items import YoutubeItem

class YoutubeSpider(scrapy.Spider):
    name = 'youtube'
    BASE_URL = 'https://www.googleapis.com/youtube/v3'

    def __init__(self):
        self.access_key = 'you_yuotube_api_access_key'
        self.video_id = 'any_youtube_video_id'

    def start_requests(self):
        params = {
            'key': self.access_key,
            'part': 'snippet,replies',
            'videoId': self.video_id,
            'maxResults': 100
        }
        url = f'{self.BASE_URL}/commentThreads/?{urllib.parse.urlencode(params)}'
        request = scrapy.Request(url, callback=self.parse)
        request.meta['params'] = params
        return [request]

    def parse(self, response):
        data = json.loads(response.body)

        # lets collect comment and reply
        items = data.get('items', [])
        for item in items:
            created_date = item['snippet']['topLevelComment']['snippet']['publishedAt']
            _created_date = datetime.datetime.strptime(created_date, '%Y-%m-%dT%H:%M:%S.000Z')
            id = item['snippet']['topLevelComment']['id']
            record = {
                'created_date': _created_date,
                'body': item['snippet']['topLevelComment']['snippet']['textOriginal'],
                'creator_name': item['snippet']['topLevelComment']['snippet'].get('authorDisplayName', {}),
                'id': id,
                'url': f'https://www.youtube.com/watch?v={self.video_id}&lc={id}',
            }

            yield YoutubeItem(**record)


        # lets paginate if next page is available for more comments
        next_page_token = data.get('nextPageToken', None)
        if next_page_token:
            params = response.meta['params']
            params['pageToken'] = next_page_token
            url = f'{self.BASE_URL}/commentThreads/?{urllib.parse.urlencode(params)}'
            request = scrapy.Request(url, callback=self.parse)
            request.meta['params'] = params
            yield request

【讨论】:

    【解决方案3】:

    要使用参数创建 GET 请求,使用 scrapy,可以使用以下示例:

    yield scrapy.FormRequest(
        url=url,
        method='GET',
        formdata=params,
        callback=self.parse_result
    )
    

    其中 'params' 是带有参数的字典。

    【讨论】:

    • 太棒了!它甚至支持使用{'a': ['val1', 'val2']} 或我认为('a', 'val1'), ('a', 'val2') 多次设置变量。 docs.scrapy.org/en/latest/topics/…
    • 这个答案避免使用外部库,对我来说,最好的。
    【解决方案4】:

    可以使用 w3lib 中的 add_or_replace_parameters。

    from w3lib.url import add_or_replace_parameters
    
    def abc(self, response):
      url = "https://yoursite.com/search/" # can be response.url or any
      params = { 
          "action": "search",
          "description": "My search here",
          "e_author": ""
      }
    
      return Request(url=add_or_replace_parameters(url, prams))
    

    【讨论】:

      【解决方案5】:

      Scrapy 不直接提供这个。您要做的是创建一个 url,您可以为此使用 urlparse 模块

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-01-23
        • 1970-01-01
        • 2016-02-24
        • 1970-01-01
        • 2023-03-25
        • 1970-01-01
        相关资源
        最近更新 更多