Pig_xiaoming 2021-04-22 09:43 采纳率: 100%
浏览 50
已采纳

Scrapy的下载中间件返回响应对象时,为什么不会执行 del 操作?

我正在编写一个 Scrapy 对接 Selenium 的下载中间件:

# Spider.py

import scrapy

class TestSpider(scrapy.Spider):
    name = 'test'
    # allowed_domains = ['xxx.com']
    start_urls = ['http://httpbin.org/']

    def parse(self, response):
        print(response)


# Middlewares.py

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.common.exceptions import TimeoutException
from fake_useragent import UserAgent
from scrapy.http import HtmlResponse


class SeleniumMiddleware:
    """对接Selenium"""

    def __init__(self):
        self.browser = webdriver.Chrome()
        self.browser.maximize_window()
        self.wait = WebDriverWait(self.browser, 10)

    @classmethod
    def from_crawler(cls, crawler):
        return cls()

    def process_request(self, request, spider):
        try:
            # 判断哪些链接需要使用selenium程序访问
            if request.url in spider.start_urls:
                self.browser.get(request.url)

                # 等待数据加载
                self.wait.until(EC.presence_of_element_located((
                    By.ID, 'operations-tag-HTTP_Methods')))

                page_text = self.browser.page_source    # 获取包含动态加载的数据

                # 返回Response对象
                return HtmlResponse(url=request.url, body=page_text, encoding='utf-8',request=request, status=200)
        except TimeoutException:
            # 超时
            return HtmlResponse(url=request.url, status=500, request=request)

    def __del__(self):
        print('游览器对象关闭~')
        self.browser.quit()

当我测试程序时,我发现当返回了响应对象,程序没有执行 del 的操作,导致打开的游览器无法如预期那样关闭。

运行结果如下:

当我将返回响应对象的代码注释的时候,程序是会执行 del 操作的。

# 返回Response对象
# return HtmlResponse(url=request.url, body=page_text, encoding='utf-8', request=request, status=200)

运行结果:

我想知道是什么原因造成这样的结果,在返回响应对象的情况下我该如何进行收尾操作(关闭游览器)?

希望您能帮帮我,感谢。

展开全部

  • 写回答

4条回答 默认 最新

  • Pig_xiaoming 2021-04-23 13:24
    关注

    已经解决,创建中间件时请使用  `spider_closed`方法并连接到信号:

    --skip--
    @classmethod
    def from_crawler(cls, crawler):
        o = cls()
        crawler.signals.connect(o.spider_closed, signals.spider_closed)
    
        return o
    
    --skip--
    
    def spider_closed(self):
        """Close the browser"""
        self.browser.quit()

    参考: https://github.com/clemfromspace/scrapy-selenium/blob/develop/scrapy_selenium/middlewares.py

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(3条)
编辑
预览

报告相同问题?

悬赏问题

  • ¥15 PADS Logic 原理图
  • ¥15 PADS Logic 图标
  • ¥15 电脑和power bi环境都是英文如何将日期层次结构转换成英文
  • ¥20 气象站点数据求取中~
  • ¥15 如何获取APP内弹出的网址链接
  • ¥15 wifi 图标不见了 不知道怎么办 上不了网 变成小地球了
手机看
程序员都在用的中文IT技术交流社区

程序员都在用的中文IT技术交流社区

专业的中文 IT 技术社区,与千万技术人共成长

专业的中文 IT 技术社区,与千万技术人共成长

关注【CSDN】视频号,行业资讯、技术分享精彩不断,直播好礼送不停!

关注【CSDN】视频号,行业资讯、技术分享精彩不断,直播好礼送不停!

客服 返回
顶部