rspec-rails 2.0.0.beta.19 → 2.0.0.beta.20
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +2 -1
- data/Gemfile +7 -0
- data/Gotchas.markdown +14 -0
- data/README.markdown +49 -9
- data/Rakefile +1 -2
- data/Upgrade.markdown +7 -0
- data/VERSION +1 -1
- data/features/controller_specs/anonymous_controller.feature +57 -19
- data/features/controller_specs/isolation_from_views.feature +2 -2
- data/features/controller_specs/readers.feature +1 -1
- data/features/controller_specs/render_views.feature +4 -4
- data/features/helper_specs/helper_spec.feature +53 -0
- data/features/mailer_specs/url_helpers.feature +2 -2
- data/features/matchers/new_record_matcher.feature +46 -1
- data/features/matchers/redirect_to_matcher.feature +41 -0
- data/features/matchers/render_template_matcher.feature +25 -0
- data/features/mocks/mock_model.feature +131 -0
- data/features/mocks/stub_model.feature +58 -0
- data/features/routing_specs/access_to_named_routes.feature +15 -0
- data/features/support/env.rb +1 -0
- data/features/view_specs/inferred_controller_path.feature +44 -0
- data/lib/generators/rspec/install/templates/spec/spec_helper.rb +4 -5
- data/lib/generators/rspec/scaffold/templates/routing_spec.rb +2 -2
- data/lib/rspec/rails.rb +1 -4
- data/lib/rspec/rails/adapters.rb +32 -6
- data/lib/rspec/rails/browser_simulators.rb +30 -0
- data/lib/rspec/rails/example.rb +2 -1
- data/lib/rspec/rails/example/controller_example_group.rb +36 -16
- data/lib/rspec/rails/example/helper_example_group.rb +8 -4
- data/lib/rspec/rails/example/mailer_example_group.rb +11 -2
- data/lib/rspec/rails/example/model_example_group.rb +1 -1
- data/lib/rspec/rails/example/rails_example_group.rb +11 -0
- data/lib/rspec/rails/example/request_example_group.rb +17 -6
- data/lib/rspec/rails/example/routing_example_group.rb +6 -1
- data/lib/rspec/rails/example/view_example_group.rb +18 -14
- data/lib/rspec/rails/matchers/be_a_new.rb +36 -1
- data/lib/rspec/rails/mocks.rb +9 -8
- data/lib/rspec/rails/tasks/rspec.rake +7 -0
- data/lib/rspec/rails/view_rendering.rb +8 -2
- data/rspec-rails.gemspec +21 -14
- data/spec/rspec/rails/assertion_adapter_spec.rb +28 -0
- data/spec/rspec/rails/example/helper_example_group_spec.rb +2 -0
- data/spec/rspec/rails/example/routing_example_group_spec.rb +17 -0
- data/spec/rspec/rails/example/view_rendering_spec.rb +56 -15
- data/spec/rspec/rails/matchers/be_a_new_spec.rb +98 -0
- data/spec/rspec/rails/matchers/errors_on_spec.rb +4 -4
- data/spec/rspec/rails/mocks/ar_classes.rb +17 -0
- data/spec/rspec/rails/mocks/stub_model_spec.rb +36 -15
- data/templates/Gemfile +2 -0
- metadata +23 -34
- data/lib/rspec/rails/monkey.rb +0 -1
- data/lib/rspec/rails/monkey/action_mailer/test_case.rb +0 -69
data/.gitignore
CHANGED
data/Gemfile
CHANGED
data/Gotchas.markdown
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
# Gotchas
|
2
|
+
|
3
|
+
## Name conflicts with upstream dependencies
|
4
|
+
|
5
|
+
Examples in rspec-rails mix in Rails' assertion modules, which mix in assertion
|
6
|
+
libraries from Minitest (if available) or Test::Unit. This makes it easy to
|
7
|
+
accidentally override a method defined in one of those upstream modules in an
|
8
|
+
example.
|
9
|
+
|
10
|
+
For example, if you have a model named `Message`, and you define a `message`
|
11
|
+
method (using `def message` or `let(:message)` in an example group, it will
|
12
|
+
override Minitest's `message` method, which is used internally by Minitest, and
|
13
|
+
is also a public API of Minitest. In this case, you would need to use a
|
14
|
+
different method name or work with instance variables instead of methods.
|
data/README.markdown
CHANGED
@@ -18,19 +18,35 @@ This installs the following gems:
|
|
18
18
|
|
19
19
|
## Configure:
|
20
20
|
|
21
|
-
Add
|
21
|
+
Add `rspec-rails` to the `:test` and `:development` groups in the Gemfile:
|
22
22
|
|
23
|
-
|
23
|
+
group :test, :development do
|
24
|
+
gem "rspec-rails", ">= 2.0.0.beta.19"
|
25
|
+
end
|
26
|
+
|
27
|
+
It needs to be in the `:development` group to expose generators and rake
|
28
|
+
tasks without having to type `RAILS_ENV=test`.
|
24
29
|
|
25
|
-
|
30
|
+
Now you can run:
|
26
31
|
|
27
|
-
script/rails
|
32
|
+
script/rails generate rspec:install
|
28
33
|
|
29
34
|
This adds the spec directory and some skeleton files, including
|
30
|
-
the "rake spec" task.
|
35
|
+
the "rake spec" task. Note that this is the only rspec generator you'll
|
36
|
+
actually see. That's because RSpec is registered with Rails as the test
|
37
|
+
framework, so whenever you generate application components like models,
|
38
|
+
controllers, etc, RSpec specs are generated instead of Test::Unit tests.
|
39
|
+
|
40
|
+
### Webrat and Capybara
|
41
|
+
|
42
|
+
You can choose between webrat or capybara for simulating a browser, automating
|
43
|
+
a browser, or setting expectations using the matchers they supply. Just add
|
44
|
+
your preference to the Gemfile:
|
31
45
|
|
32
|
-
|
33
|
-
|
46
|
+
gem "webrat"
|
47
|
+
gem "capybara"
|
48
|
+
|
49
|
+
Note that Capybara matchers are not available in view or helper specs.
|
34
50
|
|
35
51
|
## Living on edge
|
36
52
|
|
@@ -59,6 +75,8 @@ not send you to the doctor with a migraine.
|
|
59
75
|
|
60
76
|
See http://github.com/rspec/rspec-rails/issues
|
61
77
|
|
78
|
+
Also see [Gotchas.markdown](http://github.com/rspec/rspec-rails/blob/master/Gotchas.markdown)
|
79
|
+
|
62
80
|
# Request Specs
|
63
81
|
|
64
82
|
Request specs live in spec/requests.
|
@@ -129,17 +147,39 @@ View specs live in spec/views, and mix in ActionView::TestCase::Behavior.
|
|
129
147
|
rendered.should contain("Chicago")
|
130
148
|
end
|
131
149
|
end
|
132
|
-
|
150
|
+
|
151
|
+
View specs infer the controller name and path from the path to the view
|
152
|
+
template. e.g. if the template is "events/index.html.erb" then:
|
153
|
+
|
154
|
+
controller.controller_path == "events"
|
155
|
+
controller.request.path_parameters[:controller] == "events"
|
156
|
+
|
157
|
+
This means that most of the time you don't need to set these values. When
|
158
|
+
spec'ing a partial that is included across different controllers, you _may_
|
159
|
+
need to override these values before rendering the view.
|
160
|
+
|
133
161
|
## `assign(key, val)`
|
134
162
|
|
135
163
|
Use this to assign values to instance variables in the view:
|
136
164
|
|
137
165
|
assign(:widget, stub_model(Widget))
|
138
166
|
render
|
139
|
-
|
167
|
+
|
140
168
|
The code above assigns `stub_model(Widget)` to the `@widget` variable in the view, and then
|
141
169
|
renders the view.
|
142
170
|
|
171
|
+
Note that because view specs mix in `ActionView::TestCase` behavior, any
|
172
|
+
instance variables you set will be transparently propagated into your views
|
173
|
+
(similar to how instance variables you set in controller actions are made
|
174
|
+
available in views). For example:
|
175
|
+
|
176
|
+
@widget = stub_model(Widget)
|
177
|
+
render # @widget is available inside the view
|
178
|
+
|
179
|
+
RSpec doesn't officially support this pattern, which only works as a
|
180
|
+
side-effect of the inclusion of `ActionView::TestCase`. Be aware that it may be
|
181
|
+
made unavailable in the future.
|
182
|
+
|
143
183
|
### * Upgrade note
|
144
184
|
|
145
185
|
`assign(key, value)` replaces `assigns[key] = value` from rspec-rails-1.3
|
data/Rakefile
CHANGED
@@ -44,7 +44,6 @@ begin
|
|
44
44
|
gem.authors = ["David Chelimsky", "Chad Humphries"]
|
45
45
|
gem.rubyforge_project = "rspec"
|
46
46
|
gem.add_dependency "rspec", RSpec::Rails::Version::STRING
|
47
|
-
gem.add_dependency "webrat", ">= 0.7.2.beta.1"
|
48
47
|
gem.post_install_message = <<-EOM
|
49
48
|
#{"*"*50}
|
50
49
|
|
@@ -97,7 +96,7 @@ namespace :generate do
|
|
97
96
|
task :app do |t|
|
98
97
|
unless File.directory?('./tmp/example_app')
|
99
98
|
sh "bundle exec rails new ./tmp/example_app"
|
100
|
-
sh "cp ./templates/Gemfile ./tmp/example_app/"
|
99
|
+
sh "cp ./templates/Gemfile ./tmp/example_app/"
|
101
100
|
end
|
102
101
|
end
|
103
102
|
|
data/Upgrade.markdown
CHANGED
@@ -1,3 +1,10 @@
|
|
1
|
+
# Changes in beta.20
|
2
|
+
|
3
|
+
### Webrat or Capybara
|
4
|
+
|
5
|
+
rspec-rails-2.0.0.beta.20 removes the dependency and offers you a choice of
|
6
|
+
using webrat or capybara. Just add the library of your choice to your Gemfile.
|
7
|
+
|
1
8
|
# Upgrade to rspec-rails-2
|
2
9
|
|
3
10
|
## Controller specs
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
2.0.0.beta.
|
1
|
+
2.0.0.beta.20
|
@@ -6,35 +6,73 @@ Feature: anonymous controller
|
|
6
6
|
|
7
7
|
Scenario: specify error handling in ApplicationController
|
8
8
|
Given a file named "spec/controllers/application_controller_spec.rb" with:
|
9
|
-
|
10
|
-
|
9
|
+
"""
|
10
|
+
require "spec_helper"
|
11
11
|
|
12
|
-
|
13
|
-
|
12
|
+
class ApplicationController < ActionController::Base
|
13
|
+
class AccessDenied < StandardError; end
|
14
14
|
|
15
|
-
|
15
|
+
rescue_from AccessDenied, :with => :access_denied
|
16
16
|
|
17
|
-
|
17
|
+
private
|
18
|
+
|
19
|
+
def access_denied
|
20
|
+
redirect_to "/401.html"
|
21
|
+
end
|
22
|
+
end
|
18
23
|
|
19
|
-
|
20
|
-
|
24
|
+
describe ApplicationController do
|
25
|
+
controller do
|
26
|
+
def index
|
27
|
+
raise ApplicationController::AccessDenied
|
21
28
|
end
|
22
29
|
end
|
23
30
|
|
24
|
-
describe
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
end
|
31
|
+
describe "handling AccessDenied exceptions" do
|
32
|
+
it "redirects to the /401.html page" do
|
33
|
+
get :index
|
34
|
+
response.should redirect_to("/401.html")
|
29
35
|
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
"""
|
39
|
+
When I run "rspec spec"
|
40
|
+
Then the output should contain "1 example, 0 failures"
|
41
|
+
|
42
|
+
Scenario: specify error handling in subclass of ApplicationController
|
43
|
+
Given a file named "spec/controllers/application_controller_subclass_spec.rb" with:
|
44
|
+
"""
|
45
|
+
require "spec_helper"
|
46
|
+
|
47
|
+
class ApplicationController < ActionController::Base
|
48
|
+
class AccessDenied < StandardError; end
|
49
|
+
end
|
50
|
+
|
51
|
+
class ApplicationControllerSubclass < ApplicationController
|
52
|
+
|
53
|
+
rescue_from ApplicationController::AccessDenied, :with => :access_denied
|
54
|
+
|
55
|
+
private
|
56
|
+
|
57
|
+
def access_denied
|
58
|
+
redirect_to "/401.html"
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
describe ApplicationControllerSubclass do
|
63
|
+
controller(ApplicationControllerSubclass) do
|
64
|
+
def index
|
65
|
+
raise ApplicationController::AccessDenied
|
66
|
+
end
|
67
|
+
end
|
30
68
|
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
end
|
69
|
+
describe "handling AccessDenied exceptions" do
|
70
|
+
it "redirects to the /401.html page" do
|
71
|
+
get :index
|
72
|
+
response.should redirect_to("/401.html")
|
36
73
|
end
|
37
74
|
end
|
38
|
-
|
75
|
+
end
|
76
|
+
"""
|
39
77
|
When I run "rspec spec"
|
40
78
|
Then the output should contain "1 example, 0 failures"
|
@@ -9,7 +9,7 @@ Feature: do not render views
|
|
9
9
|
Scenario: expect template that is rendered by controller action (passes)
|
10
10
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
11
11
|
"""
|
12
|
-
require "spec_helper
|
12
|
+
require "spec_helper"
|
13
13
|
|
14
14
|
describe WidgetsController do
|
15
15
|
describe "index" do
|
@@ -32,7 +32,7 @@ Feature: do not render views
|
|
32
32
|
Scenario: expect template that is not rendered by controller action (fails)
|
33
33
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
34
34
|
"""
|
35
|
-
require "spec_helper
|
35
|
+
require "spec_helper"
|
36
36
|
|
37
37
|
describe WidgetsController do
|
38
38
|
describe "index" do
|
@@ -6,7 +6,7 @@ Feature: controller spec readers
|
|
6
6
|
Scenario: access controller
|
7
7
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
8
8
|
"""
|
9
|
-
require "spec_helper
|
9
|
+
require "spec_helper"
|
10
10
|
|
11
11
|
describe WidgetsController do
|
12
12
|
it "is available before an action" do
|
@@ -6,7 +6,7 @@ Feature: render views
|
|
6
6
|
Scenario: expect template that exists and is rendered by controller (passes)
|
7
7
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
8
8
|
"""
|
9
|
-
require "spec_helper
|
9
|
+
require "spec_helper"
|
10
10
|
|
11
11
|
describe WidgetsController do
|
12
12
|
render_views
|
@@ -30,14 +30,14 @@ Feature: render views
|
|
30
30
|
Scenario: expect template that does not exist and is rendered by controller (fails)
|
31
31
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
32
32
|
"""
|
33
|
-
require "spec_helper
|
33
|
+
require "spec_helper"
|
34
34
|
|
35
35
|
describe WidgetsController do
|
36
36
|
render_views
|
37
37
|
|
38
38
|
before do
|
39
39
|
def controller.index
|
40
|
-
render "other"
|
40
|
+
render :template => "other"
|
41
41
|
end
|
42
42
|
end
|
43
43
|
|
@@ -55,7 +55,7 @@ Feature: render views
|
|
55
55
|
Scenario: render_views on and off in diff contexts
|
56
56
|
Given a file named "spec/controllers/widgets_controller_spec.rb" with:
|
57
57
|
"""
|
58
|
-
require "spec_helper
|
58
|
+
require "spec_helper"
|
59
59
|
|
60
60
|
describe WidgetsController do
|
61
61
|
context "with render_views" do
|
@@ -0,0 +1,53 @@
|
|
1
|
+
Feature: helper spec
|
2
|
+
|
3
|
+
Helper specs live in spec/helpers. In order to access
|
4
|
+
the helper methods you can call them on the "helper" object.
|
5
|
+
|
6
|
+
Scenario: helper method that returns true
|
7
|
+
Given a file named "spec/helpers/application_helper_spec.rb" with:
|
8
|
+
"""
|
9
|
+
require "spec_helper"
|
10
|
+
|
11
|
+
describe ApplicationHelper do
|
12
|
+
describe "#page_title" do
|
13
|
+
it "returns true" do
|
14
|
+
helper.page_title.should be_true
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
"""
|
19
|
+
And a file named "app/helpers/application_helper.rb" with:
|
20
|
+
"""
|
21
|
+
module ApplicationHelper
|
22
|
+
def page_title
|
23
|
+
true
|
24
|
+
end
|
25
|
+
end
|
26
|
+
"""
|
27
|
+
When I run "rspec spec/helpers/application_helper_spec.rb"
|
28
|
+
Then the output should contain "1 example, 0 failures"
|
29
|
+
|
30
|
+
Scenario: helper method that accesses an instance variable
|
31
|
+
Given a file named "spec/helpers/application_helper_spec.rb" with:
|
32
|
+
"""
|
33
|
+
require "spec_helper"
|
34
|
+
|
35
|
+
describe ApplicationHelper do
|
36
|
+
describe "#page_title" do
|
37
|
+
it "returns the instance variable" do
|
38
|
+
assign(:title, "My Title")
|
39
|
+
helper.page_title.should eql("My Title")
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
"""
|
44
|
+
And a file named "app/helpers/application_helper.rb" with:
|
45
|
+
"""
|
46
|
+
module ApplicationHelper
|
47
|
+
def page_title
|
48
|
+
@title || nil
|
49
|
+
end
|
50
|
+
end
|
51
|
+
"""
|
52
|
+
When I run "rspec spec/helpers/application_helper_spec.rb"
|
53
|
+
Then the output should contain "1 example, 0 failures"
|
@@ -7,7 +7,7 @@ Feature: URL helpers in mailer examples
|
|
7
7
|
"""
|
8
8
|
And a file named "spec/mailers/notifications_spec.rb" with:
|
9
9
|
"""
|
10
|
-
require 'spec_helper
|
10
|
+
require 'spec_helper'
|
11
11
|
|
12
12
|
describe Notifications do
|
13
13
|
it 'should have access to URL helpers' do
|
@@ -25,7 +25,7 @@ Feature: URL helpers in mailer examples
|
|
25
25
|
"""
|
26
26
|
And a file named "spec/mailers/notifications_spec.rb" with:
|
27
27
|
"""
|
28
|
-
require 'spec_helper
|
28
|
+
require 'spec_helper'
|
29
29
|
|
30
30
|
describe Notifications do
|
31
31
|
it 'should have access to URL helpers' do
|
@@ -3,7 +3,10 @@ Feature: be_a_new matcher
|
|
3
3
|
The be_a_new matcher accepts a class and passes if the subject is an instance
|
4
4
|
of that class that returns true to new_record?
|
5
5
|
|
6
|
-
|
6
|
+
You can also call "with" on be_a_new with a hash of attributes to specify the
|
7
|
+
subject has equal attributes.
|
8
|
+
|
9
|
+
Scenario: example spec with four be_a_new possibilities
|
7
10
|
Given a file named "spec/models/widget_spec.rb" with:
|
8
11
|
"""
|
9
12
|
require "spec_helper"
|
@@ -23,3 +26,45 @@ Feature: be_a_new matcher
|
|
23
26
|
"""
|
24
27
|
When I run "rspec spec/models/widget_spec.rb"
|
25
28
|
Then the output should contain "4 examples, 0 failures"
|
29
|
+
|
30
|
+
Scenario: example spec using be_a_new.with
|
31
|
+
Given a file named "spec/models/widget_spec.rb" with:
|
32
|
+
"""
|
33
|
+
require "spec_helper"
|
34
|
+
|
35
|
+
class Widget < ActiveRecord::Base
|
36
|
+
establish_connection :adapter => 'sqlite3',
|
37
|
+
:database => ':memory:'
|
38
|
+
|
39
|
+
connection.execute <<-eosql
|
40
|
+
CREATE TABLE widgets (
|
41
|
+
foo_id integer,
|
42
|
+
number integer
|
43
|
+
)
|
44
|
+
eosql
|
45
|
+
end
|
46
|
+
|
47
|
+
describe Widget do
|
48
|
+
context "when initialized with attributes" do
|
49
|
+
subject { Widget.new(:foo_id => 1, :number => 1) }
|
50
|
+
|
51
|
+
it "has all of the attributes" do
|
52
|
+
should be_a_new(Widget).with(:foo_id => 1, :number => 1)
|
53
|
+
end
|
54
|
+
|
55
|
+
it "has one of the attributes" do
|
56
|
+
should be_a_new(Widget).with(:foo_id => 1)
|
57
|
+
end
|
58
|
+
|
59
|
+
it "has none of the attributes" do
|
60
|
+
should_not be_a_new(Widget).with(:blah => 'blah')
|
61
|
+
end
|
62
|
+
|
63
|
+
it "has one of the attribute values not the same" do
|
64
|
+
should_not be_a_new(Widget).with(:foo_id => 2)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
end
|
68
|
+
"""
|
69
|
+
When I run "rspec spec/models/widget_spec.rb"
|
70
|
+
Then the output should contain "4 examples, 0 failures"
|