sauce_ruby 3.5.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/bin/sauce +103 -0
- data/lib/childprocess/process.rb +34 -0
- data/lib/generators/sauce/install/install_generator.rb +54 -0
- data/lib/parallel_tests/cli_patch.rb +23 -0
- data/lib/parallel_tests/saucecucumber/runner.rb +43 -0
- data/lib/parallel_tests/saucerspec/runner.rb +40 -0
- data/lib/sauce.rb +33 -0
- data/lib/sauce/capybara.rb +189 -0
- data/lib/sauce/client.rb +40 -0
- data/lib/sauce/config.rb +434 -0
- data/lib/sauce/driver_pool.rb +5 -0
- data/lib/sauce/heroku.rb +18 -0
- data/lib/sauce/job.rb +159 -0
- data/lib/sauce/parallel.rb +16 -0
- data/lib/sauce/parallel/test_broker.rb +110 -0
- data/lib/sauce/parallel/test_group.rb +24 -0
- data/lib/sauce/railtie.rb +11 -0
- data/lib/sauce/raketasks.rb +83 -0
- data/lib/sauce/rspec/rspec.rb +186 -0
- data/lib/sauce/rspec/rspec_formatter.rb +20 -0
- data/lib/sauce/rspec/rspec_one_support.rb +66 -0
- data/lib/sauce/selenium.rb +95 -0
- data/lib/sauce/test_base.rb +21 -0
- data/lib/sauce/test_unit.rb +111 -0
- data/lib/sauce/utilities.rb +80 -0
- data/lib/sauce/utilities/connect.rb +45 -0
- data/lib/sauce/utilities/rails_server.rb +95 -0
- data/lib/sauce/utilities/rake.rb +32 -0
- data/lib/sauce/version.rb +9 -0
- data/lib/sauce/webmock.rb +16 -0
- data/lib/tasks/parallel_testing.rb +148 -0
- data/spec/cucumber_helper.rb +42 -0
- data/spec/integration/connect/spec/spec_helper.rb +21 -0
- data/spec/integration/connect/spec/start_tunnel_spec.rb +9 -0
- data/spec/integration/connect/spec/with_capybara_spec.rb +10 -0
- data/spec/integration/connect_integration_spec.rb +99 -0
- data/spec/integration/rspec-capybara/spec/capybara_required_last_spec.rb +18 -0
- data/spec/integration/rspec-capybara/spec/integration_spec.rb +17 -0
- data/spec/integration/rspec-capybara/spec/sauce_config_spec.rb +13 -0
- data/spec/integration/rspec-capybara/spec/sauce_required_last_spec.rb +21 -0
- data/spec/integration/rspec-capybara/spec/selenium/selenium_with_capybara.rb +12 -0
- data/spec/integration/rspec-capybara/spec/spec_helper.rb +37 -0
- data/spec/integration/rspec/spec/integration_spec.rb +13 -0
- data/spec/integration/rspec/spec/selenium/selenium_directory_spec.rb +20 -0
- data/spec/integration/rspec/spec/spec_helper.rb +52 -0
- data/spec/integration/rspec/spec/tagging/selenium_tagging_spec.rb +29 -0
- data/spec/integration/testunit/test/capybara_integration_test.rb +37 -0
- data/spec/integration/testunit/test/integration_test.rb +21 -0
- data/spec/integration/testunit/test/test_helper.rb +13 -0
- data/spec/parallel_tests/sauce_rspec_runner_spec.rb +23 -0
- data/spec/sauce/capybara_spec.rb +386 -0
- data/spec/sauce/config/browser_spec.rb +73 -0
- data/spec/sauce/config/config_spec.rb +400 -0
- data/spec/sauce/config/default_browsers_spec.rb +46 -0
- data/spec/sauce/config/environment_config_spec.rb +106 -0
- data/spec/sauce/config/load_defaults_spec.rb +50 -0
- data/spec/sauce/config/perfile_browser_spec.rb +105 -0
- data/spec/sauce/connect_spec.rb +21 -0
- data/spec/sauce/cucumber_spec.rb +212 -0
- data/spec/sauce/driver_pool_spec.rb +8 -0
- data/spec/sauce/file_detector_spec.rb +15 -0
- data/spec/sauce/jasmine_spec.rb +30 -0
- data/spec/sauce/parallel/test_broker_spec.rb +77 -0
- data/spec/sauce/selenium_spec.rb +60 -0
- data/spec/sauce/tasks_spec.rb +180 -0
- data/spec/sauce/utilities/rails_server_spec.rb +109 -0
- data/spec/sauce/utilities/rake_spec.rb +46 -0
- data/spec/sauce/utilities/utilities_spec.rb +137 -0
- data/spec/sauce_helper.rb +8 -0
- data/spec/spec_helper.rb +27 -0
- metadata +390 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: d0e0aad8cbfd23b54304b3b5190e3af87159e509
|
4
|
+
data.tar.gz: 35a9bc2da5f12d59c72f17a06836d9c57d3310fa
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: c27dc8ae6d754fdb7ae798b26f1cb02f234cf42937c3217ae585c484225cd3860f7b8ba929d9ecb0c2f9cc67f7ae8e449523ef35f1762723dcc5c89372278185
|
7
|
+
data.tar.gz: 6667deae41d668ac3c819ac9756ee9d92520ca97304921ff94b3f53dcccc88e3ff1a26439300590f2cd0a26fa308ef1454b588255a0982e277750ea786d9adcf
|
data/bin/sauce
ADDED
@@ -0,0 +1,103 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require 'rubygems'
|
3
|
+
require 'cmdparse'
|
4
|
+
require 'yaml'
|
5
|
+
require 'fileutils'
|
6
|
+
require 'json'
|
7
|
+
require 'highline/import'
|
8
|
+
|
9
|
+
sauce_dir = File.expand_path(File.join(File.dirname(__FILE__), '..', 'lib'))
|
10
|
+
$LOAD_PATH.unshift(sauce_dir) unless $LOAD_PATH.include?(sauce_dir)
|
11
|
+
|
12
|
+
require 'sauce'
|
13
|
+
|
14
|
+
cmd = CmdParse::CommandParser.new(true, true)
|
15
|
+
cmd.program_name = "sauce "
|
16
|
+
cmd.program_version = [0, 1, 0]
|
17
|
+
|
18
|
+
cmd.add_command(CmdParse::HelpCommand.new)
|
19
|
+
|
20
|
+
class ConnectCommand < CmdParse::Command
|
21
|
+
def usage
|
22
|
+
"Usage: #{commandparser.program_name}connect"
|
23
|
+
end
|
24
|
+
end
|
25
|
+
connect = ConnectCommand.new('connect', false)
|
26
|
+
connect.short_desc = 'Connect a Sauce Connect tunnel'
|
27
|
+
connect.set_execution_block do |args|
|
28
|
+
begin
|
29
|
+
require 'sauce/connect'
|
30
|
+
rescue LoadError
|
31
|
+
puts "Please install the sauce-connect gem (`gem install sauce-connect`) in order to use Sauce Connect"
|
32
|
+
exit 1
|
33
|
+
end
|
34
|
+
require 'sauce/config'
|
35
|
+
config = Sauce::Config.new
|
36
|
+
command = "#{Sauce::Connect.connect_command} #{config.username} #{config.access_key} #{ARGV[1 .. -1]}"
|
37
|
+
exec(command)
|
38
|
+
end
|
39
|
+
cmd.add_command(connect)
|
40
|
+
|
41
|
+
|
42
|
+
# configure
|
43
|
+
class ConfigureCommand < CmdParse::Command
|
44
|
+
def usage
|
45
|
+
"Usage: #{commandparser.program_name}configure USERNAME ACCESS_KEY"
|
46
|
+
end
|
47
|
+
end
|
48
|
+
configure = ConfigureCommand.new('configure', false)
|
49
|
+
configure.short_desc = "Configure Sauce Labs credentials"
|
50
|
+
configure.set_execution_block do |args|
|
51
|
+
if args.length < 2
|
52
|
+
puts configure.usage
|
53
|
+
exit 1
|
54
|
+
end
|
55
|
+
username = args[0]
|
56
|
+
access_key = args[1]
|
57
|
+
dir = File.join(File.expand_path("~"), ".sauce")
|
58
|
+
FileUtils.mkdir(dir) unless File.directory?(dir)
|
59
|
+
|
60
|
+
out = File.new(File.join(dir, "ondemand.yml"), 'w')
|
61
|
+
out.write(YAML.dump({"username" => username, "access_key" => access_key}))
|
62
|
+
out.close()
|
63
|
+
end
|
64
|
+
cmd.add_command(configure)
|
65
|
+
|
66
|
+
#create
|
67
|
+
create = CmdParse::Command.new('create', false)
|
68
|
+
create.short_desc = "Create a new Sauce Labs account"
|
69
|
+
create.set_execution_block do |args|
|
70
|
+
puts "Let's create a new account!"
|
71
|
+
username = ask("Username: ")
|
72
|
+
password = ask("Password: ") { |q| q.echo = "*" }
|
73
|
+
email = ask("Email: ")
|
74
|
+
name = ask("Full name: ")
|
75
|
+
|
76
|
+
body = {
|
77
|
+
:username => username,
|
78
|
+
:password => password,
|
79
|
+
:email => email,
|
80
|
+
:name => name,
|
81
|
+
:token => "c8eb3e2645005bcbbce7e2c208c6b7a71555d908"
|
82
|
+
}.to_json
|
83
|
+
|
84
|
+
begin
|
85
|
+
result = RestClient.post("http://saucelabs.com/rest/v1/users",
|
86
|
+
body, :content_type => :json, :accept => :json)
|
87
|
+
rescue => e
|
88
|
+
begin
|
89
|
+
puts "ERROR: #{JSON.load(e.response)['errors']}"
|
90
|
+
rescue
|
91
|
+
puts "ERROR: #{e.response}"
|
92
|
+
end
|
93
|
+
else
|
94
|
+
result = JSON.load(result)
|
95
|
+
|
96
|
+
puts "Account #{username} created successfully."
|
97
|
+
puts "Your access key is: #{result['access_key']}"
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
cmd.add_command(create)
|
102
|
+
|
103
|
+
cmd.parse
|
@@ -0,0 +1,34 @@
|
|
1
|
+
module ChildProcess
|
2
|
+
module Unix
|
3
|
+
class Process < AbstractProcess
|
4
|
+
|
5
|
+
def return_unless_timeout
|
6
|
+
lambda do |timeout|
|
7
|
+
begin
|
8
|
+
return poll_for_exit timeout
|
9
|
+
rescue TimeoutError
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
def stop(timeout = 3, signal=nil)
|
15
|
+
assert_started
|
16
|
+
|
17
|
+
unless signal.nil?
|
18
|
+
send_signal signal
|
19
|
+
return_unless_timeout.call(timeout)
|
20
|
+
end
|
21
|
+
|
22
|
+
send_term
|
23
|
+
return_unless_timeout.call(timeout)
|
24
|
+
|
25
|
+
send_kill
|
26
|
+
wait
|
27
|
+
rescue Errno::ECHILD, Errno::ESRCH
|
28
|
+
# handle race condition where process dies between timeout
|
29
|
+
# and send_kill
|
30
|
+
true
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
module Sauce
|
2
|
+
module Generators
|
3
|
+
class InstallGenerator < Rails::Generators::Base
|
4
|
+
source_root File.expand_path("../templates", __FILE__)
|
5
|
+
|
6
|
+
desc "Prep application for Sauce OnDemand Selenium tests"
|
7
|
+
|
8
|
+
argument :username, :type => :string, :required => false
|
9
|
+
argument :api_key, :type => :string, :required => false
|
10
|
+
|
11
|
+
def copy_rake_tasks
|
12
|
+
copy_file "sauce.rake", "lib/tasks/sauce.rake"
|
13
|
+
end
|
14
|
+
|
15
|
+
def configure_credentials
|
16
|
+
if username
|
17
|
+
system("sauce config #{username} #{api_key}")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def setup_spec
|
22
|
+
if File.directory? 'spec'
|
23
|
+
empty_directory "spec/selenium"
|
24
|
+
append_file "spec/spec_helper.rb", generate_config
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
def setup_test
|
29
|
+
if File.directory? 'test'
|
30
|
+
empty_directory "test/selenium"
|
31
|
+
append_file "test/test_helper.rb", generate_config
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
private
|
36
|
+
|
37
|
+
def generate_config
|
38
|
+
return <<-CONFIG
|
39
|
+
|
40
|
+
require 'sauce'
|
41
|
+
|
42
|
+
Sauce.config do |conf|
|
43
|
+
conf[:browsers] = [
|
44
|
+
["Windows 2003", "firefox", "3.6."]
|
45
|
+
]
|
46
|
+
conf[:application_host] = "127.0.0.1"
|
47
|
+
conf[:application_port] = "3001"
|
48
|
+
conf[:browser_url] = "http://localhost:3001/"
|
49
|
+
end
|
50
|
+
CONFIG
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module ParallelTests
|
2
|
+
class CLI
|
3
|
+
def run_tests_in_parallel(num_processes, options)
|
4
|
+
test_results = nil
|
5
|
+
|
6
|
+
report_time_taken do
|
7
|
+
groups = @runner.tests_in_groups(options[:files], num_processes, options)
|
8
|
+
non_empty_groups = groups.reject {|group| group.empty?}
|
9
|
+
Sauce::TestBroker.test_groups = non_empty_groups
|
10
|
+
|
11
|
+
report_number_of_tests(non_empty_groups)
|
12
|
+
|
13
|
+
test_results = execute_in_parallel(non_empty_groups, non_empty_groups.size, options) do |group|
|
14
|
+
run_tests(group, Sauce::TestBroker.group_index(group), num_processes, options)
|
15
|
+
end
|
16
|
+
|
17
|
+
report_results(test_results)
|
18
|
+
end
|
19
|
+
|
20
|
+
abort final_fail_message if any_test_failed?(test_results)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
require "parallel_tests/cucumber/runner"
|
2
|
+
|
3
|
+
module ParallelTests
|
4
|
+
module Saucecucumber
|
5
|
+
class Runner < ParallelTests::Cucumber::Runner
|
6
|
+
|
7
|
+
def self.run_tests(test_files, process_number, num_processes, options)
|
8
|
+
options = options.dup
|
9
|
+
sanitized_test_files = test_files.map { |val| Shellwords.escape(val) }
|
10
|
+
env = Sauce::TestBroker.next_environment(test_files)
|
11
|
+
env.merge!({"AUTOTEST" => "1"}) if $stdout.tty? # display color when we are in a terminal
|
12
|
+
options.merge!({:env => env})
|
13
|
+
cmd = [
|
14
|
+
executable,
|
15
|
+
(runtime_logging if File.directory?(File.dirname(runtime_log))),
|
16
|
+
cucumber_opts(options[:test_options]),
|
17
|
+
*sanitized_test_files
|
18
|
+
].compact.join(" ")
|
19
|
+
execute_command(cmd, process_number, num_processes, options)
|
20
|
+
end
|
21
|
+
|
22
|
+
def self.tests_in_groups(tests, num_groups, options={})
|
23
|
+
originals = (options[:group_by] == :steps) ? Grouper.by_steps(find_tests(tests, options), num_groups, options) : super
|
24
|
+
all_tests = originals.flatten * Sauce::TestBroker.test_platforms(:cucumber).length
|
25
|
+
base_group_size = all_tests.length / num_groups
|
26
|
+
num_full_groups = all_tests.length - (base_group_size * num_groups)
|
27
|
+
|
28
|
+
curpos = 0
|
29
|
+
groups = []
|
30
|
+
num_groups.times do |i|
|
31
|
+
group_size = base_group_size
|
32
|
+
if i < num_full_groups
|
33
|
+
group_size += 1
|
34
|
+
end
|
35
|
+
groups << all_tests.slice(curpos, group_size)
|
36
|
+
curpos += group_size
|
37
|
+
end
|
38
|
+
|
39
|
+
groups
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
require "yaml"
|
2
|
+
require "parallel_tests/rspec/runner"
|
3
|
+
|
4
|
+
module ParallelTests
|
5
|
+
module Saucerspec
|
6
|
+
class Runner < ParallelTests::RSpec::Runner
|
7
|
+
|
8
|
+
def self.run_tests(test_files, process_number, num_processes, options)
|
9
|
+
our_options = options.dup
|
10
|
+
exe = executable # expensive, so we cache
|
11
|
+
version = (exe =~ /\brspec\b/ ? 2 : 1)
|
12
|
+
cmd = [exe, our_options[:test_options], (rspec_2_color if version == 2), spec_opts, *test_files].compact.join(" ")
|
13
|
+
env = Sauce::TestBroker.next_environment(test_files)
|
14
|
+
env << " #{rspec_1_color}" if version == 1
|
15
|
+
our_options.merge!(:env => env)
|
16
|
+
execute_command(cmd, process_number, num_processes, our_options)
|
17
|
+
end
|
18
|
+
|
19
|
+
|
20
|
+
def self.tests_in_groups(tests, num_groups, options={})
|
21
|
+
all_tests = super.flatten * Sauce::TestBroker.test_platforms(:rspec).length
|
22
|
+
base_group_size = all_tests.length / num_groups
|
23
|
+
num_full_groups = all_tests.length - (base_group_size * num_groups)
|
24
|
+
|
25
|
+
curpos = 0
|
26
|
+
groups = []
|
27
|
+
num_groups.times do |i|
|
28
|
+
group_size = base_group_size
|
29
|
+
if i < num_full_groups
|
30
|
+
group_size += 1
|
31
|
+
end
|
32
|
+
groups << all_tests.slice(curpos, group_size)
|
33
|
+
curpos += group_size
|
34
|
+
end
|
35
|
+
|
36
|
+
groups
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
data/lib/sauce.rb
ADDED
@@ -0,0 +1,33 @@
|
|
1
|
+
if defined?(Rails)
|
2
|
+
require "sauce/railtie"
|
3
|
+
else
|
4
|
+
require 'tasks/parallel_testing'
|
5
|
+
end
|
6
|
+
|
7
|
+
require 'sauce/version'
|
8
|
+
require 'sauce/utilities'
|
9
|
+
require 'sauce/utilities/rake'
|
10
|
+
require 'sauce/job'
|
11
|
+
require 'sauce/client'
|
12
|
+
require 'sauce/config'
|
13
|
+
require 'sauce/selenium'
|
14
|
+
require 'sauce/test_base'
|
15
|
+
require 'sauce/rspec/rspec'
|
16
|
+
require 'sauce/test_unit'
|
17
|
+
require 'parallel_tests/saucerspec/runner'
|
18
|
+
require 'parallel_tests/saucecucumber/runner'
|
19
|
+
|
20
|
+
|
21
|
+
# Ruby before 1.9.3-p382 does not handle exit codes correctly when nested
|
22
|
+
if RUBY_VERSION == "1.9.3" && RUBY_PATCHLEVEL < 392
|
23
|
+
module Kernel
|
24
|
+
alias :existing_at_exit :at_exit
|
25
|
+
def at_exit(&block)
|
26
|
+
existing_at_exit do
|
27
|
+
exit_status = $!.status if $!.is_a?(SystemExit)
|
28
|
+
block.call
|
29
|
+
exit exit_status if exit_status
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,189 @@
|
|
1
|
+
require 'capybara'
|
2
|
+
require 'sauce/config'
|
3
|
+
require 'sauce/selenium'
|
4
|
+
require 'sauce/version'
|
5
|
+
|
6
|
+
|
7
|
+
$sauce_tunnel = nil
|
8
|
+
|
9
|
+
module Sauce
|
10
|
+
module Capybara
|
11
|
+
class Driver < ::Capybara::Selenium::Driver
|
12
|
+
RETRY_ON = [::Selenium::WebDriver::Error::UnhandledError,
|
13
|
+
::Selenium::WebDriver::Error::UnknownError]
|
14
|
+
MAX_RETRIES = 3
|
15
|
+
|
16
|
+
def handle_retry(method, *args, &block)
|
17
|
+
retries = 0
|
18
|
+
|
19
|
+
# Disable retries only when we really really want to, this will remain
|
20
|
+
# an undocomented hack for the time being
|
21
|
+
if ENV['SAUCE_DISABLE_RETRY']
|
22
|
+
retries = MAX_RETRIES
|
23
|
+
end
|
24
|
+
|
25
|
+
begin
|
26
|
+
send("base_#{method}".to_sym, *args, &block)
|
27
|
+
rescue *RETRY_ON => e
|
28
|
+
if retries < MAX_RETRIES
|
29
|
+
puts "Received an exception (#{e}), retrying"
|
30
|
+
retries = retries + 1
|
31
|
+
retry
|
32
|
+
else
|
33
|
+
raise
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
alias :base_visit :visit
|
39
|
+
alias :base_current_url :current_url
|
40
|
+
alias :base_within_frame :within_frame
|
41
|
+
alias :base_within_window :within_window
|
42
|
+
alias :base_find_window :find_window
|
43
|
+
alias :base_execute_script :execute_script
|
44
|
+
alias :base_evaluate_script :evaluate_script
|
45
|
+
|
46
|
+
@methods_to_retry = [:visit, :current_url,
|
47
|
+
:within_frame, :within_window, :find_window, :source,
|
48
|
+
:execute_script, :evaluate_script
|
49
|
+
]
|
50
|
+
|
51
|
+
if method_defined? :find
|
52
|
+
alias :base_find :find
|
53
|
+
@methods_to_retry += [:find]
|
54
|
+
else
|
55
|
+
alias :base_find_css :find_css
|
56
|
+
alias :base_find_xpath :find_xpath
|
57
|
+
@methods_to_retry += [:find_css, :find_xpath]
|
58
|
+
end
|
59
|
+
|
60
|
+
if Gem::Version.new(::Capybara::VERSION) < Gem::Version.new(2)
|
61
|
+
alias :base_body :body
|
62
|
+
alias :base_source :source
|
63
|
+
|
64
|
+
@methods_to_retry + [:body, :source]
|
65
|
+
else
|
66
|
+
alias :base_html :html
|
67
|
+
@methods_to_retry + [:html]
|
68
|
+
end
|
69
|
+
|
70
|
+
@methods_to_retry.each do |method|
|
71
|
+
define_method(method) do |*args, &block|
|
72
|
+
handle_retry(method, *args, &block)
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
# Oh gods why didn't I comment these when I wrote them?
|
77
|
+
# These are what I think I'm doing.
|
78
|
+
#
|
79
|
+
# Returns the browser currently being used or fetches a new
|
80
|
+
# browser, either from the RSpec integration or by creating
|
81
|
+
# one.
|
82
|
+
def browser
|
83
|
+
# Return the existing browser if we have it
|
84
|
+
unless existing_browser?
|
85
|
+
# Try to get a driver from the driver pool
|
86
|
+
@browser = rspec_browser
|
87
|
+
unless @browser
|
88
|
+
@browser = Sauce::Selenium2.new
|
89
|
+
at_exit do
|
90
|
+
finish!
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
@browser
|
95
|
+
end
|
96
|
+
|
97
|
+
# Returns the rspec created browser if it exists
|
98
|
+
def rspec_browser
|
99
|
+
if browser = Sauce.driver_pool[Thread.current.object_id]
|
100
|
+
@using_rspec_browser = true
|
101
|
+
else
|
102
|
+
@using_rspec_browser = false
|
103
|
+
end
|
104
|
+
browser
|
105
|
+
end
|
106
|
+
|
107
|
+
# If a browser has been created OR RSpec has put one in the diriver pool
|
108
|
+
# and we're using that browser, returns true.
|
109
|
+
def existing_browser?
|
110
|
+
if @using_rspec_browser
|
111
|
+
@browser == Sauce.driver_pool[Thread.current.object_id]
|
112
|
+
else
|
113
|
+
@browser
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
def finish!
|
118
|
+
@browser.quit if existing_browser?
|
119
|
+
@browser = nil
|
120
|
+
|
121
|
+
# Rethink how to do this. RSpec still references the driver pool.
|
122
|
+
Sauce.driver_pool[Thread.current.object_id] = nil
|
123
|
+
@using_rspec_browser = nil
|
124
|
+
end
|
125
|
+
|
126
|
+
def render(path)
|
127
|
+
browser.save_screenshot path
|
128
|
+
end
|
129
|
+
end
|
130
|
+
|
131
|
+
def self.configure_capybara
|
132
|
+
::Capybara.configure do |config|
|
133
|
+
if Sauce::Config.new[:start_local_application]
|
134
|
+
config.server_port = Sauce::Config.get_application_port
|
135
|
+
end
|
136
|
+
begin
|
137
|
+
#config.always_include_port = true
|
138
|
+
rescue
|
139
|
+
# This option is only in Capybara 2+
|
140
|
+
end
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
def self.configure_capybara_for_rspec
|
145
|
+
begin
|
146
|
+
require "rspec/core"
|
147
|
+
::RSpec.configure do |config|
|
148
|
+
config.before :suite do
|
149
|
+
::Capybara.configure do |capy_config|
|
150
|
+
sauce_config = Sauce::Config.new
|
151
|
+
if capy_config.app_host.nil?
|
152
|
+
if sauce_config[:start_local_application]
|
153
|
+
host = sauce_config[:application_host] || "127.0.0.1"
|
154
|
+
port = sauce_config[:application_port]
|
155
|
+
capy_config.app_host = "http://#{host}:#{port}"
|
156
|
+
capy_config.run_server = false
|
157
|
+
end
|
158
|
+
end
|
159
|
+
end
|
160
|
+
end
|
161
|
+
end
|
162
|
+
rescue LoadError => e
|
163
|
+
# User is not using RSpec
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|
168
|
+
|
169
|
+
Capybara.register_driver :sauce do |app|
|
170
|
+
driver = Sauce::Capybara::Driver.new(app)
|
171
|
+
end
|
172
|
+
|
173
|
+
Sauce::Capybara.configure_capybara
|
174
|
+
|
175
|
+
# Monkeypatch Capybara to not use :selenium driver
|
176
|
+
require 'capybara/dsl'
|
177
|
+
module Capybara
|
178
|
+
def self.javascript_driver
|
179
|
+
@javascript_driver || :sauce
|
180
|
+
end
|
181
|
+
end
|
182
|
+
|
183
|
+
module Sauce
|
184
|
+
module RSpec
|
185
|
+
module SeleniumExampleGroup
|
186
|
+
Sauce::Capybara.configure_capybara_for_rspec
|
187
|
+
end
|
188
|
+
end
|
189
|
+
end
|