sauce 0.9.0 → 0.10.0
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.
- data/README.markdown +111 -20
- data/VERSION +1 -1
- data/bin/sauce +5 -1
- data/generators/sauce/sauce_generator.rb +57 -0
- data/generators/sauce/templates/sauce.rake +51 -0
- data/lib/sauce/config.rb +1 -1
- data/lib/sauce/connect.rb +1 -1
- data/lib/sauce/integrations.rb +34 -1
- metadata +6 -4
data/README.markdown
CHANGED
@@ -7,48 +7,139 @@ Features
|
|
7
7
|
--------
|
8
8
|
Current:
|
9
9
|
|
10
|
-
*
|
11
|
-
*
|
10
|
+
* Drop-in replacement for Selenium::Client::Driver that takes care of connecting to Sauce OnDemand
|
11
|
+
* RSpec, Test::Unit, and Rails integration for tests, including automatic setup of Sauce Connect
|
12
|
+
* ActiveRecord-like interface for tunnels and jobs: Find/create/destroy
|
12
13
|
|
13
14
|
Planned:
|
14
15
|
|
15
16
|
* Extend to automatic retrieval of jobs logs, videos, reverse tunnels
|
16
17
|
* Start/stop local instances of Sauce RC
|
18
|
+
* Webrat integration
|
17
19
|
|
18
20
|
Install
|
19
21
|
-------
|
20
22
|
`gem install sauce`
|
21
23
|
|
22
|
-
|
24
|
+
`sauce config USERNAME ACCESS_KEY`
|
25
|
+
|
26
|
+
Examples
|
23
27
|
-------
|
24
|
-
|
28
|
+
### Selenium Client driver
|
25
29
|
require 'rubygems'
|
26
30
|
require 'sauce'
|
31
|
+
selenium = Sauce::Selenium.new(:browser_url => "http://saucelabs.com",
|
32
|
+
:browser => "firefox", :browser_version => "3.", :os => "Windows 2003",
|
33
|
+
:job_name => "My first test!")
|
34
|
+
selenium.start
|
35
|
+
selenium.open "/"
|
36
|
+
selenium.stop
|
37
|
+
|
38
|
+
### RSpec integration
|
39
|
+
#!/usr/bin/env ruby
|
40
|
+
#
|
41
|
+
# Sample RSpec test case using the Sauce gem
|
42
|
+
#
|
43
|
+
require "rubygems"
|
44
|
+
require "sauce"
|
45
|
+
|
46
|
+
# This should go in your spec_helper.rb file if you have one
|
47
|
+
Sauce.config do |config|
|
48
|
+
config.browser_url = "http://saucelabs.com/"
|
49
|
+
config.browsers = [
|
50
|
+
["Linux", "firefox", "3.6."]
|
51
|
+
]
|
52
|
+
|
53
|
+
# uncomment this if your server is not publicly accessible
|
54
|
+
#config.application_host = "localhost"
|
55
|
+
#config.application_port = "80"
|
56
|
+
end
|
57
|
+
|
58
|
+
# If this goes in spec/selenium/foo_spec.rb, you can omit the :type parameter
|
59
|
+
describe "The Sauce Labs website", :type => :selenium do
|
60
|
+
it "should have a home page" do
|
61
|
+
page.open "/"
|
62
|
+
page.is_text_present("Sauce Labs").should be_true
|
63
|
+
end
|
27
64
|
|
28
|
-
|
29
|
-
|
30
|
-
|
65
|
+
it "should have a pricing page" do
|
66
|
+
page.open "/"
|
67
|
+
page.click "link=Pricing"
|
68
|
+
page.wait_for_page_to_load 30000
|
69
|
+
page.is_text_present("Free Trial").should be_true
|
70
|
+
end
|
71
|
+
end
|
31
72
|
|
32
|
-
|
33
|
-
|
73
|
+
### Test::Unit integration
|
74
|
+
#!/usr/bin/env ruby
|
75
|
+
#
|
76
|
+
# Sample Test:Unit test case using the Sauce gem
|
77
|
+
#
|
78
|
+
require "test/unit"
|
79
|
+
require "rubygems"
|
80
|
+
require "sauce"
|
34
81
|
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
82
|
+
# This should go in your test_helper.rb file if you have one
|
83
|
+
Sauce.config do |config|
|
84
|
+
config.browser_url = "http://saucelabs.com/"
|
85
|
+
config.browsers = [
|
86
|
+
["Linux", "firefox", "3.6."]
|
87
|
+
]
|
88
|
+
|
89
|
+
# uncomment this if your server is not publicly accessible
|
90
|
+
#config.application_host = "localhost"
|
91
|
+
#config.application_port = "80"
|
92
|
+
end
|
93
|
+
|
94
|
+
class ExampleTest < Sauce::TestCase
|
95
|
+
def test_sauce
|
96
|
+
page.open "/"
|
97
|
+
assert page.title.include?("Sauce Labs")
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
### Rails integration
|
102
|
+
You can use either RSpec or Test::Unit with Rails and Sauce OnDemand.
|
103
|
+
The generator will take care of setting up your helpers with Sauce OnDemand
|
104
|
+
configuration, which you can tweak inside the `Sauce.config` block.
|
105
|
+
|
106
|
+
`gem install sauce`
|
107
|
+
|
108
|
+
`script/generate sauce USERNAME ACCESS_KEY`
|
109
|
+
|
110
|
+
For RSpec, drop something like this in spec/selenium:
|
111
|
+
|
112
|
+
require "spec_helper"
|
113
|
+
|
114
|
+
describe "my app" do
|
115
|
+
it "should have a home page" do
|
116
|
+
page.open "/"
|
117
|
+
page.is_text_present("Welcome Aboard").should be_true
|
118
|
+
end
|
119
|
+
end
|
120
|
+
|
121
|
+
For Test::Unit, drop something like this in test/selenium:
|
122
|
+
|
123
|
+
require "test_helper"
|
124
|
+
|
125
|
+
class DemoTest < Sauce::RailsTestCase
|
126
|
+
test "my app", do
|
127
|
+
page.open "/"
|
128
|
+
page.is_text_present("Welcome Aboard").should be_true
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
To run your tests, use rake:
|
133
|
+
|
134
|
+
`rake spec:selenium:sauce`
|
44
135
|
|
45
|
-
|
136
|
+
`rake test:selenium:sauce`
|
46
137
|
|
47
138
|
Note on Patches/Pull Requests
|
48
139
|
-----------------------------
|
49
140
|
* Fork the project.
|
50
141
|
* Make your feature addition or bug fix.
|
51
|
-
* Add tests for it. This is important so
|
142
|
+
* Add tests for it. This is important so we don't break it in a future version unintentionally.
|
52
143
|
* Commit, do not mess with rakefile, version, or history. (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
|
53
144
|
* Send me a pull request. Bonus points for topic branches.
|
54
145
|
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.10.0
|
data/bin/sauce
CHANGED
@@ -3,6 +3,7 @@
|
|
3
3
|
require 'rubygems'
|
4
4
|
require 'cmdparse'
|
5
5
|
require 'yaml'
|
6
|
+
require 'fileutils'
|
6
7
|
|
7
8
|
sauce_dir = File.expand_path(File.join(File.dirname(__FILE__), '..', 'lib'))
|
8
9
|
$LOAD_PATH.unshift(sauce_dir) unless $LOAD_PATH.include?(sauce_dir)
|
@@ -30,7 +31,10 @@ else
|
|
30
31
|
end
|
31
32
|
username = args[0]
|
32
33
|
access_key = args[1]
|
33
|
-
|
34
|
+
dir = File.join(File.expand_path("~"), ".sauce")
|
35
|
+
FileUtils.mkdir(dir) unless File.directory?(dir)
|
36
|
+
|
37
|
+
out = File.new(File.join(dir, "ondemand.yml"), 'w')
|
34
38
|
out.write(YAML.dump({"username" => username, "access_key" => access_key}))
|
35
39
|
out.close()
|
36
40
|
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require 'sauce/config'
|
2
|
+
|
3
|
+
# This generator bootstraps a Rails project for use with Sauce OnDemand
|
4
|
+
class SauceGenerator < Rails::Generator::Base
|
5
|
+
def initialize(runtime_args, runtime_options = {})
|
6
|
+
config = Sauce::Config.new
|
7
|
+
if config.username.nil? || config.access_key.nil?
|
8
|
+
if runtime_args.size < 2
|
9
|
+
raise "Usage: #{$0} sauce <USERNAME> <ACCESS_KEY>"
|
10
|
+
else
|
11
|
+
system("sauce config #{runtime_args[0]} #{runtime_args[1]}")
|
12
|
+
end
|
13
|
+
end
|
14
|
+
super
|
15
|
+
end
|
16
|
+
|
17
|
+
def manifest
|
18
|
+
record do |m|
|
19
|
+
if File.directory? 'spec'
|
20
|
+
m.directory File.join('spec', 'selenium') if File.directory? 'spec'
|
21
|
+
m.setup_helper(File.join('spec', 'spec_helper.rb')) if File.directory? 'spec'
|
22
|
+
end
|
23
|
+
|
24
|
+
m.directory File.join('lib', 'tasks')
|
25
|
+
m.directory File.join('test', 'selenium') if File.directory? 'test'
|
26
|
+
m.file 'sauce.rake', File.join('lib', 'tasks', 'sauce.rake')
|
27
|
+
m.setup_helper(File.join('test', 'test_helper.rb'))
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def setup_helper(file)
|
32
|
+
contents = File.read(file)
|
33
|
+
if contents !~ /Sauce.config/
|
34
|
+
File.open(file, "a") do |file|
|
35
|
+
file.write <<-CONFIG
|
36
|
+
|
37
|
+
require 'sauce'
|
38
|
+
|
39
|
+
Sauce.config do |conf|
|
40
|
+
conf.browser_url = "http://#{rand(100000)}.test/"
|
41
|
+
conf.browsers = [
|
42
|
+
["Windows 2003", "firefox", "3."]
|
43
|
+
]
|
44
|
+
conf.application_host = "127.0.0.1"
|
45
|
+
conf.application_port = "3001"
|
46
|
+
end
|
47
|
+
CONFIG
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
protected
|
53
|
+
|
54
|
+
def banner
|
55
|
+
"Usage: #{$0} sauce [<USERNAME> <ACCESS_KEY>]"
|
56
|
+
end
|
57
|
+
end
|
@@ -0,0 +1,51 @@
|
|
1
|
+
spec_prereq = File.exist?(File.join(RAILS_ROOT, 'config', 'database.yml')) ? "db:test:prepare" : :noop
|
2
|
+
task :noop do
|
3
|
+
end
|
4
|
+
|
5
|
+
namespace :spec do
|
6
|
+
namespace :selenium do
|
7
|
+
desc "Run the Selenium acceptance tests in spec/selenium using Sauce OnDemand"
|
8
|
+
task :sauce => spec_prereq do
|
9
|
+
server = IO.popen("script/server RAILS_ENV=test --port 3001")
|
10
|
+
begin
|
11
|
+
Rake::Task["spec:selenium:runtests"].invoke
|
12
|
+
ensure
|
13
|
+
Process.kill("INT", server.pid)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
desc "" # Hide it from rake -T
|
18
|
+
Spec::Rake::SpecTask.new :runtests do |t|
|
19
|
+
t.spec_opts = ['--options', "\"#{RAILS_ROOT}/spec/spec.opts\""]
|
20
|
+
t.spec_files = FileList["spec/selenium/**/*_spec.rb"]
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
task :selenium => "selenium:sauce"
|
25
|
+
end
|
26
|
+
|
27
|
+
namespace :test do
|
28
|
+
namespace :selenium do
|
29
|
+
desc "Run the Selenium acceptance tests in test/selenium using Sauce OnDemand"
|
30
|
+
task :sauce do
|
31
|
+
server = IO.popen("script/server --port 3001")
|
32
|
+
begin
|
33
|
+
Rake::Task["test:selenium:runtests"].invoke
|
34
|
+
ensure
|
35
|
+
Process.kill("INT", server.pid)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
Rake::TestTask.new(:runtests) do |t|
|
40
|
+
t.libs << "test"
|
41
|
+
t.pattern = 'test/selenium/**/*_test.rb'
|
42
|
+
t.verbose = true
|
43
|
+
end
|
44
|
+
desc "" # Hide it from rake -T
|
45
|
+
Rake::Task['test:selenium:runtests'].instance_variable_set(:@full_comment, nil)
|
46
|
+
Rake::Task['test:selenium:runtests'].instance_variable_set(:@comment, nil)
|
47
|
+
Rake::Task['test:selenium:runtests'].enhance(["db:test:prepare"])
|
48
|
+
end
|
49
|
+
|
50
|
+
task :selenium => "selenium:sauce"
|
51
|
+
end
|
data/lib/sauce/config.rb
CHANGED
@@ -92,7 +92,7 @@ module Sauce
|
|
92
92
|
"ondemand.yml",
|
93
93
|
File.join("config", "ondemand.yml"),
|
94
94
|
File.join(File.dirname(File.dirname(File.expand_path(File.dirname(__FILE__)))), "ondemand.yml"),
|
95
|
-
File.join(
|
95
|
+
File.join(File.expand_path("~"), ".sauce", "ondemand.yml")
|
96
96
|
]
|
97
97
|
|
98
98
|
paths.each do |path|
|
data/lib/sauce/connect.rb
CHANGED
@@ -11,7 +11,7 @@ module Sauce
|
|
11
11
|
options.delete(:host)
|
12
12
|
options.delete(:port)
|
13
13
|
config = Sauce::Config.new(options)
|
14
|
-
args = ['-u', config.username, '-k', config.access_key, '-s', host, '-p', port, '-d', config.domain]
|
14
|
+
args = ['-u', config.username, '-k', config.access_key, '-s', host, '-p', port, '-d', config.domain, '-t', '80']
|
15
15
|
@pipe = IO.popen(([Sauce::Connect.find_sauce_connect] + args).join(' '))
|
16
16
|
at_exit do
|
17
17
|
Process.kill("INT", @pipe.pid)
|
data/lib/sauce/integrations.rb
CHANGED
@@ -49,7 +49,7 @@ rescue LoadError
|
|
49
49
|
end
|
50
50
|
|
51
51
|
begin
|
52
|
-
require 'test/unit'
|
52
|
+
require 'test/unit/testcase'
|
53
53
|
module Sauce
|
54
54
|
class TestCase < Test::Unit::TestCase
|
55
55
|
attr_reader :selenium
|
@@ -110,3 +110,36 @@ begin
|
|
110
110
|
rescue LoadError
|
111
111
|
# User doesn't have Test::Unit installed
|
112
112
|
end
|
113
|
+
|
114
|
+
if defined?(ActiveSupport::TestCase)
|
115
|
+
module Sauce
|
116
|
+
class RailsTestCase < ::ActiveSupport::TestCase
|
117
|
+
attr_reader :selenium
|
118
|
+
|
119
|
+
alias_method :page, :selenium
|
120
|
+
alias_method :s, :selenium
|
121
|
+
|
122
|
+
def run(*args, &blk)
|
123
|
+
unless name =~ /^default_test/
|
124
|
+
config = Sauce::Config.new
|
125
|
+
config.browsers.each do |os, browser, version|
|
126
|
+
@selenium = Sauce::Selenium.new({:os => os, :browser => browser, :browser_version => version,
|
127
|
+
:job_name => "#{name}"})
|
128
|
+
@selenium.start
|
129
|
+
super(*args, &blk)
|
130
|
+
@selenium.stop
|
131
|
+
end
|
132
|
+
end
|
133
|
+
end
|
134
|
+
|
135
|
+
# Placeholder so test/unit ignores test cases without any tests.
|
136
|
+
def default_test
|
137
|
+
end
|
138
|
+
|
139
|
+
def self.ensure_tunnel_running
|
140
|
+
unless defined?(@tunnel)
|
141
|
+
end
|
142
|
+
end
|
143
|
+
end
|
144
|
+
end
|
145
|
+
end
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sauce
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 55
|
5
5
|
prerelease: false
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
-
-
|
8
|
+
- 10
|
9
9
|
- 0
|
10
|
-
version: 0.
|
10
|
+
version: 0.10.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Sean Grove
|
@@ -16,7 +16,7 @@ autorequire:
|
|
16
16
|
bindir: bin
|
17
17
|
cert_chain: []
|
18
18
|
|
19
|
-
date: 2010-
|
19
|
+
date: 2010-11-02 00:00:00 -07:00
|
20
20
|
default_executable: sauce
|
21
21
|
dependencies:
|
22
22
|
- !ruby/object:Gem::Dependency
|
@@ -145,6 +145,8 @@ files:
|
|
145
145
|
- examples/saucelabs_spec.rb
|
146
146
|
- examples/test_saucelabs.rb
|
147
147
|
- examples/test_saucelabs2.rb
|
148
|
+
- generators/sauce/sauce_generator.rb
|
149
|
+
- generators/sauce/templates/sauce.rake
|
148
150
|
- lib/sauce.rb
|
149
151
|
- lib/sauce/client.rb
|
150
152
|
- lib/sauce/config.rb
|