diff --git a/lib/capybara/poltergeist.rb b/lib/capybara/poltergeist.rb index 7da9b31..f6b086a 100644 --- a/lib/capybara/poltergeist.rb +++ b/lib/capybara/poltergeist.rb @@ -10,6 +10,7 @@ module Capybara autoload :WebSocketServer, 'capybara/poltergeist/web_socket_server' autoload :Client, 'capybara/poltergeist/client' autoload :Util, 'capybara/poltergeist/util' + autoload :Inspector, 'capybara/poltergeist/inspector' require 'capybara/poltergeist/errors' end diff --git a/lib/capybara/poltergeist/client.rb b/lib/capybara/poltergeist/client.rb index 1cd1944..f32c063 100644 --- a/lib/capybara/poltergeist/client.rb +++ b/lib/capybara/poltergeist/client.rb @@ -2,16 +2,9 @@ require 'sfl' module Capybara::Poltergeist class Client - INSPECTOR_BROWSERS = %w(chromium chromium-browser google-chrome safari) - PHANTOMJS_SCRIPT = File.expand_path('../client/compiled/main.js', __FILE__) - PHANTOMJS_VERSION = '1.4.1' - PHANTOMJS_NAME = 'phantomjs' - - def self.inspector_browser - @inspector_browser ||= INSPECTOR_BROWSERS.find do |name| - system "which #{name} &>/dev/null" - end - end + PHANTOMJS_SCRIPT = File.expand_path('../client/compiled/main.js', __FILE__) + PHANTOMJS_VERSION = '1.4.1' + PHANTOMJS_NAME = 'phantomjs' def self.start(*args) client = new(*args) @@ -21,7 +14,7 @@ module Capybara::Poltergeist attr_reader :pid, :port, :path, :inspector - def initialize(port, inspector = false, path = nil) + def initialize(port, inspector = nil, path = nil) @port = port @inspector = inspector @path = path || PHANTOMJS_NAME @@ -31,11 +24,6 @@ module Capybara::Poltergeist def start check_phantomjs_version @pid = Kernel.spawn(command) - - # Opens a remote debugger for the phantomjs session. This feature - # is unfinished / experimental. When the debugger opens, you have - # to type __run() into the console to get it going. - Kernel.spawn(inspector_command) if inspector end def stop @@ -50,29 +38,18 @@ module Capybara::Poltergeist def command @command ||= begin parts = [path] - parts << "--remote-debugger-port=#{inspector_port}" if inspector + + if inspector + parts << "--remote-debugger-port=#{inspector.port}" + parts << "--remote-debugger-autorun=yes" + end + parts << PHANTOMJS_SCRIPT parts << port parts.join(" ") end end - def inspector_port - @inspector_port ||= Util.find_available_port - end - - def inspector_command - "#{inspector_browser} http://localhost:#{inspector_port}/webkit/inspector/inspector.html?page=1" - end - - def inspector_browser - if inspector == true - self.class.inspector_browser or raise "webkit browser not found; please specify it explicitly" - else - inspector - end - end - private def check_phantomjs_version diff --git a/lib/capybara/poltergeist/driver.rb b/lib/capybara/poltergeist/driver.rb index f4fe496..24d4c38 100644 --- a/lib/capybara/poltergeist/driver.rb +++ b/lib/capybara/poltergeist/driver.rb @@ -15,10 +15,14 @@ module Capybara::Poltergeist @browser ||= Browser.new( :logger => logger, :phantomjs => options[:phantomjs], - :inspector => options[:inspector] + :inspector => inspector ) end + def inspector + @inspector ||= options[:inspector] && Inspector.new(options[:inspector]) + end + def restart browser.restart end @@ -73,6 +77,16 @@ module Capybara::Poltergeist browser.resize(width, height) end + def debug + inspector.open + pause + end + + def pause + STDERR.puts "Poltergeist execution paused. Press enter to continue." + STDIN.gets + end + def wait? true end diff --git a/lib/capybara/poltergeist/inspector.rb b/lib/capybara/poltergeist/inspector.rb new file mode 100644 index 0000000..3edea46 --- /dev/null +++ b/lib/capybara/poltergeist/inspector.rb @@ -0,0 +1,35 @@ +module Capybara::Poltergeist + class Inspector + BROWSERS = %w(chromium chromium-browser google-chrome safari) + + def self.detect_browser + @browser ||= BROWSERS.find { |name| system("which #{name} &>/dev/null") } + end + + def initialize(browser = nil) + @browser = browser.respond_to?(:to_str) ? browser : nil + end + + def browser + @browser ||= self.class.detect_browser + end + + def port + @port ||= Util.find_available_port + end + + def url + "http://localhost:#{port}/" + end + + def open + if browser + Kernel.spawn("#{browser} #{url}") + else + raise Error, "Could not find a browser executable to open #{url}. " \ + "You can specify one manually using e.g. `:inspector => 'chromium'` " \ + "as a configuration option for Poltergeist." + end + end + end +end diff --git a/spec/unit/driver_spec.rb b/spec/unit/driver_spec.rb index 0d9c95e..2fc8ab8 100644 --- a/spec/unit/driver_spec.rb +++ b/spec/unit/driver_spec.rb @@ -8,6 +8,10 @@ module Capybara::Poltergeist it 'should not log' do subject.logger.should == nil end + + it 'has no inspector' do + subject.inspector.should be_nil + end end context 'with a :logger option' do @@ -25,5 +29,15 @@ module Capybara::Poltergeist subject.logger.should == STDERR end end + + context 'with an :inspector option' do + subject { Driver.new(nil, :inspector => 'foo') } + + it 'has an inspector' do + subject.inspector.should_not be_nil + subject.inspector.should be_a(Inspector) + subject.inspector.browser.should == 'foo' + end + end end end diff --git a/spec/unit/inspector_spec.rb b/spec/unit/inspector_spec.rb new file mode 100644 index 0000000..54d0589 --- /dev/null +++ b/spec/unit/inspector_spec.rb @@ -0,0 +1,39 @@ +require 'spec_helper' + +module Capybara::Poltergeist + describe Inspector do + it 'detects a browser by default' do + Inspector.stub(:detect_browser => 'chromium') + Inspector.new.browser.should == 'chromium' + Inspector.new(true).browser.should == 'chromium' + end + + it 'allows a browser to be specified' do + Inspector.new('foo').browser.should == 'foo' + end + + it 'finds a port to run on' do + subject.port.should_not be_nil + end + + it 'remembers the port' do + subject.port.should == subject.port + end + + it 'has a url' do + subject.stub(:port => 1234) + subject.url.should == "http://localhost:1234/" + end + + it 'can be opened' do + subject.stub(:port => 1234, :browser => 'chromium') + Kernel.should_receive(:spawn).with("chromium http://localhost:1234/") + subject.open + end + + it 'raises an error on open when the browser is unknown' do + subject.stub(:port => 1234, :browser => nil) + expect { subject.open }.to raise_error(Capybara::Poltergeist::Error) + end + end +end