简体   繁体   English

Capybara / Selenium-在每次调用时强制重新加载Selenium Driver

[英]Capybara/Selenium - force to reload Selenium Driver on each call

I have a solution to parse some data from a remote websites using Firefox(46) + Capybara + Selenium. 我有一个解决方案,可以使用Firefox(46)+ Capybara + Selenium解析来自远程网站的一些数据。 I pass path_to_firefox_profile argument on initialize, which is some real Firefox profile folder. 我在初始化时传递path_to_firefox_profile参数,这是一些真实的Firefox配置文件文件夹。

The problem is that if I execute this code: 问题是,如果我执行以下代码:

a = MyParser.new(profile_a)
a.parse_something
b = MyParser.new(profile_b)
b.parse_something

... the instance b will have profile A loaded despite I specified another profile. ...尽管我指定了另一个配置文件,实例b仍将加载配置文件A。

But, if I run these 2 lines in a separate processes, I'll get what I want. 但是,如果我在单独的过程中运行这两行,我会得到想要的。 So I assume one of them - either Capybara or Selenium - stores profiles settings once per ruby process, and won't change it on demand. 因此,我假设其中之一-Capybara或Selenium-在每个红宝石处理过程中存储一次配置文件设置,并且不会按需更改它。

Are there are ideas how to change profile within the same process? 是否有想法在同一过程中更改配置文件?

I tries to .quit Firefox, but it doesn't help, on visiting new URL Selenium opens another Firefox window with the exact same profile instead of new one. 我尝试.quit Firefox,但这样做无济于事,在访问新URL时Selenium将打开另一个Firefox窗口,该窗口具有完全相同的配置文件而不是新的配置文件。

class MyParser
  def initialize(path_to_firefox_profile)
    Capybara.register_driver(:selenium) do |app|
      client = Selenium::WebDriver::Remote::Http::Default.new
      client.timeout = 150
      Capybara::Selenium::Driver.new(app,
        profile: path_to_firefox_profile,
        http_client: client)
    end
  end

  def parse_something
    # perform some parsings & return result
  end
end

Capybara's register_driver registers the driver by the name you assign globally, and will use those drivers (by name) in its sessions. Capybara的register_driver通过您在全局分配的名称来注册驱动程序,并将在其会话中使用这些驱动程序(按名称)。 It will also automatically manage sessions in a manner designed for ease of use by people testing web-apps. 它还将以一种易于测试Web应用程序的人易于使用的方式自动管理会话。 The issue here is that a new session with the newly registered driver isn't being created. 这里的问题是没有创建与新注册驱动程序的新会话。 This is because you're not really using Capybara for what it was designed, and therefore need to pick up a bit more of the weight of session management. 这是因为您并未真正将Capybara用于其设计目的,因此需要承担更多会话管理的任务。 If you're ever going to have more than 2 of your MyParser objects around you probably should be creating a new session per MyParser instance you create and then using that session in all of the MyParser methods. 如果您周围将有两个以上的MyParser对象,则可能应该为您创建的每个MyParser实例创建一个新会话,然后在所有MyParser方法中使用该会话。 Since you're using different driver settings per MyParser instance you should probably also be naming each driver registered differently. 由于每个MyParser实例使用的驱动程序设置不同,因此您可能还应该为每个注册的驱动程序命名不同。

class MyParser
  def initialize(path_to_firefox_profile)
    Capybara.register_driver(self.object_id.to_s) do |app|
      client = Selenium::WebDriver::Remote::Http::Default.new
      client.timeout = 150
      Capybara::Selenium::Driver.new(app,
        profile: path_to_firefox_profile,
        http_client: client)
    end
    @session = Capybara::Session.new(self.object_id.to_s)
  end

  def parse_something
    @session.visit("some url")
    @session.find(...)  # perform some parsings & return result
  end
end

You will also need to handle cleaning up the session when you're done with each MyParser instance. 每个MyParser实例完成后,您还需要清理会话。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM