francois-shoulda 2.0.5.4 → 2.10.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (109) hide show
  1. data/README.rdoc +60 -10
  2. data/Rakefile +7 -7
  3. data/lib/shoulda.rb +7 -15
  4. data/lib/shoulda/action_controller.rb +28 -0
  5. data/lib/shoulda/action_controller/helpers.rb +47 -0
  6. data/lib/shoulda/action_controller/macros.rb +277 -0
  7. data/lib/shoulda/action_controller/matchers.rb +37 -0
  8. data/lib/shoulda/action_controller/matchers/assign_to_matcher.rb +109 -0
  9. data/lib/shoulda/action_controller/matchers/filter_param_matcher.rb +57 -0
  10. data/lib/shoulda/action_controller/matchers/render_with_layout_matcher.rb +81 -0
  11. data/lib/shoulda/action_controller/matchers/respond_with_content_type_matcher.rb +70 -0
  12. data/lib/shoulda/action_controller/matchers/respond_with_matcher.rb +81 -0
  13. data/lib/shoulda/action_controller/matchers/route_matcher.rb +93 -0
  14. data/lib/shoulda/action_controller/matchers/set_session_matcher.rb +87 -0
  15. data/lib/shoulda/action_controller/matchers/set_the_flash_matcher.rb +85 -0
  16. data/lib/shoulda/action_mailer.rb +1 -1
  17. data/lib/shoulda/action_mailer/assertions.rb +32 -33
  18. data/lib/shoulda/action_view.rb +10 -0
  19. data/lib/shoulda/action_view/macros.rb +56 -0
  20. data/lib/shoulda/active_record.rb +6 -2
  21. data/lib/shoulda/active_record/assertions.rb +62 -89
  22. data/lib/shoulda/active_record/helpers.rb +40 -0
  23. data/lib/shoulda/active_record/macros.rb +520 -684
  24. data/lib/shoulda/active_record/matchers.rb +42 -0
  25. data/lib/shoulda/active_record/matchers/allow_mass_assignment_of_matcher.rb +83 -0
  26. data/lib/shoulda/active_record/matchers/allow_value_matcher.rb +102 -0
  27. data/lib/shoulda/active_record/matchers/association_matcher.rb +226 -0
  28. data/lib/shoulda/active_record/matchers/ensure_inclusion_of_matcher.rb +87 -0
  29. data/lib/shoulda/active_record/matchers/ensure_length_of_matcher.rb +141 -0
  30. data/lib/shoulda/active_record/matchers/have_db_column_matcher.rb +169 -0
  31. data/lib/shoulda/active_record/matchers/have_index_matcher.rb +105 -0
  32. data/lib/shoulda/active_record/matchers/have_named_scope_matcher.rb +125 -0
  33. data/lib/shoulda/active_record/matchers/have_readonly_attribute_matcher.rb +59 -0
  34. data/lib/shoulda/active_record/matchers/validate_acceptance_of_matcher.rb +41 -0
  35. data/lib/shoulda/active_record/matchers/validate_numericality_of_matcher.rb +39 -0
  36. data/lib/shoulda/active_record/matchers/validate_presence_of_matcher.rb +60 -0
  37. data/lib/shoulda/active_record/matchers/validate_uniqueness_of_matcher.rb +148 -0
  38. data/lib/shoulda/active_record/matchers/validation_matcher.rb +56 -0
  39. data/lib/shoulda/assertions.rb +50 -40
  40. data/lib/shoulda/autoload_macros.rb +46 -0
  41. data/lib/shoulda/context.rb +124 -126
  42. data/lib/shoulda/helpers.rb +5 -7
  43. data/lib/shoulda/macros.rb +63 -64
  44. data/lib/shoulda/private_helpers.rb +16 -18
  45. data/lib/shoulda/rails.rb +5 -11
  46. data/lib/shoulda/rspec.rb +11 -0
  47. data/lib/shoulda/tasks/list_tests.rake +6 -1
  48. data/lib/shoulda/test_unit.rb +19 -0
  49. data/rails/init.rb +7 -1
  50. data/test/README +2 -2
  51. data/test/fail_macros.rb +15 -15
  52. data/test/fixtures/tags.yml +1 -1
  53. data/test/functional/posts_controller_test.rb +46 -26
  54. data/test/functional/users_controller_test.rb +0 -19
  55. data/test/matchers/active_record/allow_mass_assignment_of_matcher_test.rb +68 -0
  56. data/test/matchers/active_record/allow_value_matcher_test.rb +41 -0
  57. data/test/matchers/active_record/association_matcher_test.rb +258 -0
  58. data/test/matchers/active_record/ensure_inclusion_of_matcher_test.rb +80 -0
  59. data/test/matchers/active_record/ensure_length_of_matcher_test.rb +158 -0
  60. data/test/matchers/active_record/have_db_column_matcher_test.rb +169 -0
  61. data/test/matchers/active_record/have_index_matcher_test.rb +74 -0
  62. data/test/matchers/active_record/have_named_scope_matcher_test.rb +65 -0
  63. data/test/matchers/active_record/have_readonly_attributes_matcher_test.rb +29 -0
  64. data/test/matchers/active_record/validate_acceptance_of_matcher_test.rb +44 -0
  65. data/test/matchers/active_record/validate_numericality_of_matcher_test.rb +52 -0
  66. data/test/matchers/active_record/validate_presence_of_matcher_test.rb +86 -0
  67. data/test/matchers/active_record/validate_uniqueness_of_matcher_test.rb +147 -0
  68. data/test/matchers/controller/assign_to_matcher_test.rb +35 -0
  69. data/test/matchers/controller/filter_param_matcher_test.rb +32 -0
  70. data/test/matchers/controller/render_with_layout_matcher_test.rb +33 -0
  71. data/test/matchers/controller/respond_with_content_type_matcher_test.rb +27 -0
  72. data/test/matchers/controller/respond_with_matcher_test.rb +106 -0
  73. data/test/matchers/controller/route_matcher_test.rb +58 -0
  74. data/test/matchers/controller/set_session_matcher_test.rb +31 -0
  75. data/test/matchers/controller/set_the_flash_matcher.rb +41 -0
  76. data/test/model_builder.rb +106 -0
  77. data/test/other/autoload_macro_test.rb +18 -0
  78. data/test/other/helpers_test.rb +58 -0
  79. data/test/other/private_helpers_test.rb +1 -1
  80. data/test/other/should_test.rb +16 -16
  81. data/test/rails_root/app/controllers/posts_controller.rb +6 -5
  82. data/test/rails_root/app/models/pets/dog.rb +10 -0
  83. data/test/rails_root/app/models/treat.rb +3 -0
  84. data/test/rails_root/app/models/user.rb +4 -3
  85. data/test/rails_root/app/views/layouts/posts.rhtml +2 -0
  86. data/test/rails_root/config/database.yml +1 -1
  87. data/test/rails_root/config/environment.rb +1 -1
  88. data/test/rails_root/config/environments/{sqlite3.rb → test.rb} +0 -0
  89. data/test/rails_root/db/migrate/001_create_users.rb +3 -2
  90. data/test/rails_root/db/migrate/011_create_treats.rb +12 -0
  91. data/test/rails_root/test/shoulda_macros/custom_macro.rb +6 -0
  92. data/test/rails_root/vendor/gems/gem_with_macro-0.0.1/shoulda_macros/gem_macro.rb +6 -0
  93. data/test/rails_root/vendor/plugins/plugin_with_macro/shoulda_macros/plugin_macro.rb +6 -0
  94. data/test/rspec_test.rb +207 -0
  95. data/test/test_helper.rb +3 -1
  96. data/test/unit/address_test.rb +1 -23
  97. data/test/unit/dog_test.rb +5 -2
  98. data/test/unit/post_test.rb +7 -3
  99. data/test/unit/product_test.rb +2 -2
  100. data/test/unit/tag_test.rb +2 -1
  101. data/test/unit/user_test.rb +25 -9
  102. metadata +84 -23
  103. data/lib/shoulda/controller.rb +0 -30
  104. data/lib/shoulda/controller/formats/html.rb +0 -201
  105. data/lib/shoulda/controller/formats/xml.rb +0 -170
  106. data/lib/shoulda/controller/helpers.rb +0 -64
  107. data/lib/shoulda/controller/macros.rb +0 -316
  108. data/lib/shoulda/controller/resource_options.rb +0 -236
  109. data/test/rails_root/app/models/dog.rb +0 -5
@@ -1,170 +0,0 @@
1
- module ThoughtBot # :nodoc:
2
- module Shoulda # :nodoc:
3
- module Controller # :nodoc:
4
- module XML
5
- def self.included(other) #:nodoc:
6
- other.class_eval do
7
- extend ThoughtBot::Shoulda::Controller::XML::ClassMethods
8
- end
9
- end
10
-
11
- module ClassMethods
12
- # Macro that creates a test asserting that the controller responded with an XML content-type
13
- # and that the XML contains +<name/>+ as the root element.
14
- def should_respond_with_xml_for(name = nil)
15
- should "have ContentType set to 'application/xml'" do
16
- assert_xml_response
17
- end
18
-
19
- if name
20
- should "return <#{name}/> as the root element" do
21
- body = @response.body.first(100).map {|l| " #{l}"}
22
- assert_select name.to_s.dasherize, 1, "Body:\n#{body}...\nDoes not have <#{name}/> as the root element."
23
- end
24
- end
25
- end
26
- alias should_respond_with_xml should_respond_with_xml_for
27
-
28
- protected
29
-
30
- def make_show_xml_tests(res) # :nodoc:
31
- context "on GET to #{controller_name_from_class}#show as xml" do
32
- setup do
33
- request_xml
34
- record = get_existing_record(res)
35
- parent_params = make_parent_params(res, record)
36
- get :show, parent_params.merge({ res.identifier => record.to_param })
37
- end
38
-
39
- if res.denied.actions.include?(:show)
40
- should_not_assign_to res.object
41
- should_respond_with 401
42
- else
43
- should_assign_to res.object
44
- should_respond_with :success
45
- should_respond_with_xml_for res.object
46
- end
47
- end
48
- end
49
-
50
- def make_edit_xml_tests(res) # :nodoc:
51
- # XML doesn't need an :edit action
52
- end
53
-
54
- def make_new_xml_tests(res) # :nodoc:
55
- # XML doesn't need a :new action
56
- end
57
-
58
- def make_index_xml_tests(res) # :nodoc:
59
- context "on GET to #{controller_name_from_class}#index as xml" do
60
- setup do
61
- request_xml
62
- parent_params = make_parent_params(res)
63
- get(:index, parent_params)
64
- end
65
-
66
- if res.denied.actions.include?(:index)
67
- should_not_assign_to res.object.to_s.pluralize
68
- should_respond_with 401
69
- else
70
- should_respond_with :success
71
- should_respond_with_xml_for res.object.to_s.pluralize
72
- should_assign_to res.object.to_s.pluralize
73
- end
74
- end
75
- end
76
-
77
- def make_destroy_xml_tests(res) # :nodoc:
78
- context "on DELETE to #{controller_name_from_class}#destroy as xml" do
79
- setup do
80
- request_xml
81
- @record = get_existing_record(res)
82
- parent_params = make_parent_params(res, @record)
83
- delete :destroy, parent_params.merge({ res.identifier => @record.to_param })
84
- end
85
-
86
- if res.denied.actions.include?(:destroy)
87
- should_respond_with 401
88
-
89
- should "not destroy record" do
90
- assert @record.reload
91
- end
92
- else
93
- should "destroy record" do
94
- assert_raises(::ActiveRecord::RecordNotFound, "@#{res.object} was not destroyed.") do
95
- @record.reload
96
- end
97
- end
98
- end
99
- end
100
- end
101
-
102
- def make_create_xml_tests(res) # :nodoc:
103
- context "on POST to #{controller_name_from_class}#create as xml" do
104
- setup do
105
- request_xml
106
- parent_params = make_parent_params(res)
107
- @count = res.klass.count
108
- post :create, parent_params.merge(res.object => res.create.params)
109
- end
110
-
111
- if res.denied.actions.include?(:create)
112
- should_respond_with 401
113
- should_not_assign_to res.object
114
-
115
- should "not create new record" do
116
- assert_equal @count, res.klass.count
117
- end
118
- else
119
- should_assign_to res.object
120
-
121
- should "not have errors on @#{res.object}" do
122
- assert_equal [], pretty_error_messages(assigns(res.object)), "@#{res.object} has errors:"
123
- end
124
- end
125
- end
126
- end
127
-
128
- def make_update_xml_tests(res) # :nodoc:
129
- context "on PUT to #{controller_name_from_class}#update as xml" do
130
- setup do
131
- request_xml
132
- @record = get_existing_record(res)
133
- parent_params = make_parent_params(res, @record)
134
- put :update, parent_params.merge(res.identifier => @record.to_param, res.object => res.update.params)
135
- end
136
-
137
- if res.denied.actions.include?(:update)
138
- should_not_assign_to res.object
139
- should_respond_with 401
140
- else
141
- should_assign_to res.object
142
-
143
- should "not have errors on @#{res.object}" do
144
- assert_equal [], assigns(res.object).errors.full_messages, "@#{res.object} has errors:"
145
- end
146
- end
147
- end
148
- end
149
- end
150
-
151
- # Sets the next request's format to 'application/xml'
152
- def request_xml
153
- @request.accept = "application/xml"
154
- end
155
-
156
- # Asserts that the controller's response was 'application/xml'
157
- def assert_xml_response
158
- content_type = (@response.headers["Content-Type"] || @response.headers["type"]).to_s
159
- regex = %r{\bapplication/xml\b}
160
-
161
- msg = "Content Type '#{content_type.inspect}' doesn't match '#{regex.inspect}'\n"
162
- msg += "Body: #{@response.body.first(100).chomp} ..."
163
-
164
- assert_match regex, content_type, msg
165
- end
166
-
167
- end
168
- end
169
- end
170
- end
@@ -1,64 +0,0 @@
1
- module ThoughtBot # :nodoc:
2
- module Shoulda # :nodoc:
3
- module Controller # :nodoc:
4
- module Helpers # :nodoc:
5
- private # :enddoc:
6
-
7
- SPECIAL_INSTANCE_VARIABLES = %w{
8
- _cookies
9
- _flash
10
- _headers
11
- _params
12
- _request
13
- _response
14
- _session
15
- action_name
16
- before_filter_chain_aborted
17
- cookies
18
- flash
19
- headers
20
- ignore_missing_templates
21
- logger
22
- params
23
- request
24
- request_origin
25
- response
26
- session
27
- template
28
- template_class
29
- template_root
30
- url
31
- variables_added
32
- }.map(&:to_s)
33
-
34
- def instantiate_variables_from_assigns(*names, &blk)
35
- old = {}
36
- names = (@response.template.assigns.keys - SPECIAL_INSTANCE_VARIABLES) if names.empty?
37
- names.each do |name|
38
- old[name] = instance_variable_get("@#{name}")
39
- instance_variable_set("@#{name}", assigns(name.to_sym))
40
- end
41
- blk.call
42
- names.each do |name|
43
- instance_variable_set("@#{name}", old[name])
44
- end
45
- end
46
-
47
- def get_existing_record(res) # :nodoc:
48
- returning(instance_variable_get("@#{res.object}")) do |record|
49
- assert(record, "This test requires you to set @#{res.object} in your setup block")
50
- end
51
- end
52
-
53
- def make_parent_params(resource, record = nil, parent_names = nil) # :nodoc:
54
- parent_names ||= resource.parents.reverse
55
- return {} if parent_names == [] # Base case
56
- parent_name = parent_names.shift
57
- parent = record ? record.send(parent_name) : parent_name.to_s.classify.constantize.find(:first)
58
-
59
- { :"#{parent_name}_id" => parent.to_param }.merge(make_parent_params(resource, parent, parent_names))
60
- end
61
- end
62
- end
63
- end
64
- end
@@ -1,316 +0,0 @@
1
- module ThoughtBot # :nodoc:
2
- module Shoulda # :nodoc:
3
- module Controller # :nodoc:
4
- # = Macro test helpers for your controllers
5
- #
6
- # By using the macro helpers you can quickly and easily create concise and easy to read test suites.
7
- #
8
- # This code segment:
9
- # context "on GET to :show for first record" do
10
- # setup do
11
- # get :show, :id => 1
12
- # end
13
- #
14
- # should_assign_to :user
15
- # should_respond_with :success
16
- # should_render_template :show
17
- # should_not_set_the_flash
18
- #
19
- # should "do something else really cool" do
20
- # assert_equal 1, assigns(:user).id
21
- # end
22
- # end
23
- #
24
- # Would produce 5 tests for the +show+ action
25
- #
26
- # Furthermore, the should_be_restful helper will create an entire set of tests which will verify that your
27
- # controller responds restfully to a variety of requested formats.
28
- module Macros
29
- # <b>DEPRECATED:</b> Please see
30
- # http://thoughtbot.lighthouseapp.com/projects/5807/tickets/78 for more
31
- # information.
32
- #
33
- # Generates a full suite of tests for a restful controller.
34
- #
35
- # The following definition will generate tests for the +index+, +show+, +new+,
36
- # +edit+, +create+, +update+ and +destroy+ actions, in both +html+ and +xml+ formats:
37
- #
38
- # should_be_restful do |resource|
39
- # resource.parent = :user
40
- #
41
- # resource.create.params = { :title => "first post", :body => 'blah blah blah'}
42
- # resource.update.params = { :title => "changed" }
43
- # end
44
- #
45
- # This generates about 40 tests, all of the format:
46
- # "on GET to :show should assign @user."
47
- # "on GET to :show should not set the flash."
48
- # "on GET to :show should render 'show' template."
49
- # "on GET to :show should respond with success."
50
- # "on GET to :show as xml should assign @user."
51
- # "on GET to :show as xml should have ContentType set to 'application/xml'."
52
- # "on GET to :show as xml should respond with success."
53
- # "on GET to :show as xml should return <user/> as the root element."
54
- # The +resource+ parameter passed into the block is a ResourceOptions object, and
55
- # is used to configure the tests for the details of your resources.
56
- #
57
- def should_be_restful(&blk) # :yields: resource
58
- warn "[DEPRECATION] should_be_restful is deprecated. Please see http://thoughtbot.lighthouseapp.com/projects/5807/tickets/78 for more information."
59
-
60
- resource = ResourceOptions.new
61
- blk.call(resource)
62
- resource.normalize!(self)
63
-
64
- resource.formats.each do |format|
65
- resource.actions.each do |action|
66
- if self.respond_to? :"make_#{action}_#{format}_tests"
67
- self.send(:"make_#{action}_#{format}_tests", resource)
68
- else
69
- should "test #{action} #{format}" do
70
- flunk "Test for #{action} as #{format} not implemented"
71
- end
72
- end
73
- end
74
- end
75
- end
76
-
77
- # :section: Test macros
78
- # Macro that creates a test asserting that the flash contains the given value.
79
- # val can be a String, a Regex, or nil (indicating that the flash should not be set)
80
- #
81
- # Example:
82
- #
83
- # should_set_the_flash_to "Thank you for placing this order."
84
- # should_set_the_flash_to /created/i
85
- # should_set_the_flash_to nil
86
- def should_set_the_flash_to(val)
87
- if val
88
- should "have #{val.inspect} in the flash" do
89
- assert_contains flash.values, val, ", Flash: #{flash.inspect}"
90
- end
91
- else
92
- should "not set the flash" do
93
- assert_equal({}, flash, "Flash was set to:\n#{flash.inspect}")
94
- end
95
- end
96
- end
97
-
98
- # Macro that creates a test asserting that the flash is empty. Same as
99
- # @should_set_the_flash_to nil@
100
- def should_not_set_the_flash
101
- should_set_the_flash_to nil
102
- end
103
-
104
- # Macro that creates a test asserting that filter_parameter_logging
105
- # is set for the specified keys
106
- #
107
- # Example:
108
- #
109
- # should_filter_params :password, :ssn
110
- def should_filter_params(*keys)
111
- keys.each do |key|
112
- should "filter #{key}" do
113
- assert @controller.respond_to?(:filter_parameters),
114
- "The key #{key} is not filtered"
115
- filtered = @controller.send(:filter_parameters, {key.to_s => key.to_s})
116
- assert_equal '[FILTERED]', filtered[key.to_s],
117
- "The key #{key} is not filtered"
118
- end
119
- end
120
- end
121
-
122
- # Macro that creates a test asserting that the controller assigned to
123
- # each of the named instance variable(s).
124
- #
125
- # Options:
126
- # * <tt>:class</tt> - The expected class of the instance variable being checked.
127
- # * <tt>:equals</tt> - A string which is evaluated and compared for equality with
128
- # the instance variable being checked.
129
- #
130
- # Example:
131
- #
132
- # should_assign_to :user, :posts
133
- # should_assign_to :user, :class => User
134
- # should_assign_to :user, :equals => '@user'
135
- def should_assign_to(*names)
136
- opts = names.extract_options!
137
- names.each do |name|
138
- test_name = "assign @#{name}"
139
- test_name << " as class #{opts[:class]}" if opts[:class]
140
- test_name << " which is equal to #{opts[:equals]}" if opts[:equals]
141
- should test_name do
142
- assigned_value = assigns(name.to_sym)
143
- assert assigned_value, "The action isn't assigning to @#{name}"
144
- assert_kind_of opts[:class], assigned_value if opts[:class]
145
- if opts[:equals]
146
- instantiate_variables_from_assigns do
147
- expected_value = eval(opts[:equals], self.send(:binding), __FILE__, __LINE__)
148
- assert_equal expected_value, assigned_value,
149
- "Instance variable @#{name} expected to be #{expected_value}" +
150
- " but was #{assigned_value}"
151
- end
152
- end
153
- end
154
- end
155
- end
156
-
157
- # Macro that creates a test asserting that the controller did not assign to
158
- # any of the named instance variable(s).
159
- #
160
- # Example:
161
- #
162
- # should_not_assign_to :user, :posts
163
- def should_not_assign_to(*names)
164
- names.each do |name|
165
- should "not assign to @#{name}" do
166
- assert !assigns(name.to_sym), "@#{name} was visible"
167
- end
168
- end
169
- end
170
-
171
- # Macro that creates a test asserting that the controller responded with a 'response' status code.
172
- # Example:
173
- #
174
- # should_respond_with :success
175
- def should_respond_with(response)
176
- should "respond with #{response}" do
177
- assert_response response
178
- end
179
- end
180
-
181
- # Macro that creates a test asserting that the response content type was 'content_type'.
182
- # Example:
183
- #
184
- # should_respond_with_content_type 'application/rss+xml'
185
- # should_respond_with_content_type :rss
186
- # should_respond_with_content_type /rss/
187
- def should_respond_with_content_type(content_type)
188
- should "respond with content type of #{content_type}" do
189
- content_type = Mime::EXTENSION_LOOKUP[content_type.to_s].to_s if content_type.is_a? Symbol
190
- if content_type.is_a? Regexp
191
- assert_match content_type, @response.content_type, "Expected to match #{content_type} but was actually #{@response.content_type}"
192
- else
193
- assert_equal content_type, @response.content_type, "Expected #{content_type} but was actually #{@response.content_type}"
194
- end
195
- end
196
- end
197
-
198
- # Macro that creates a test asserting that a value returned from the session is correct.
199
- # The given string is evaled to produce the resulting redirect path. All of the instance variables
200
- # set by the controller are available to the evaled string.
201
- # Example:
202
- #
203
- # should_return_from_session :user_id, '@user.id'
204
- # should_return_from_session :message, '"Free stuff"'
205
- def should_return_from_session(key, expected)
206
- should "return the correct value from the session for key #{key}" do
207
- instantiate_variables_from_assigns do
208
- expected_value = eval(expected, self.send(:binding), __FILE__, __LINE__)
209
- assert_equal expected_value, session[key], "Expected #{expected_value.inspect} but was #{session[key]}"
210
- end
211
- end
212
- end
213
-
214
- # Macro that creates a test asserting that the controller rendered the given template.
215
- # Example:
216
- #
217
- # should_render_template :new
218
- def should_render_template(template)
219
- should "render template #{template.inspect}" do
220
- assert_template template.to_s
221
- end
222
- end
223
-
224
- # Macro that creates a test asserting that the controller rendered with the given layout.
225
- # Example:
226
- #
227
- # should_render_with_layout 'special'
228
- def should_render_with_layout(expected_layout = 'application')
229
- if expected_layout
230
- should "render with #{expected_layout.inspect} layout" do
231
- response_layout = @response.layout.blank? ? "" : @response.layout.split('/').last
232
- assert_equal expected_layout.to_s,
233
- response_layout,
234
- "Expected to render with layout #{expected_layout} but was rendered with #{response_layout}"
235
- end
236
- else
237
- should "render without layout" do
238
- assert_nil @response.layout,
239
- "Expected no layout, but was rendered using #{@response.layout}"
240
- end
241
- end
242
- end
243
-
244
- # Macro that creates a test asserting that the controller rendered without a layout.
245
- # Same as @should_render_with_layout false@
246
- def should_render_without_layout
247
- should_render_with_layout nil
248
- end
249
-
250
- # Macro that creates a test asserting that the controller returned a redirect to the given path.
251
- # The given string is evaled to produce the resulting redirect path. All of the instance variables
252
- # set by the controller are available to the evaled string.
253
- # Example:
254
- #
255
- # should_redirect_to '"/"'
256
- # should_redirect_to "user_url(@user)"
257
- # should_redirect_to "users_url"
258
- def should_redirect_to(url)
259
- should "redirect to #{url.inspect}" do
260
- instantiate_variables_from_assigns do
261
- assert_redirected_to eval(url, self.send(:binding), __FILE__, __LINE__)
262
- end
263
- end
264
- end
265
-
266
- # Macro that creates a test asserting that the rendered view contains a <form> element.
267
- def should_render_a_form
268
- should "display a form" do
269
- assert_select "form", true, "The template doesn't contain a <form> element"
270
- end
271
- end
272
-
273
- # Macro that creates a routing test. It tries to use the given HTTP
274
- # +method+ on the given +path+, and asserts that it routes to the
275
- # given +options+.
276
- #
277
- # If you don't specify a :controller, it will try to guess the controller
278
- # based on the current test.
279
- #
280
- # +to_param+ is called on the +options+ given.
281
- #
282
- # Examples:
283
- #
284
- # should_route :get, "/posts", :controller => :posts, :action => :index
285
- # should_route :get, "/posts/new", :action => :new
286
- # should_route :post, "/posts", :action => :create
287
- # should_route :get, "/posts/1", :action => :show, :id => 1
288
- # should_route :edit, "/posts/1", :action => :show, :id => 1
289
- # should_route :put, "/posts/1", :action => :update, :id => 1
290
- # should_route :delete, "/posts/1", :action => :destroy, :id => 1
291
- # should_route :get, "/users/1/posts/1",
292
- # :action => :show, :id => 1, :user_id => 1
293
- #
294
- def should_route(method, path, options)
295
- unless options[:controller]
296
- options[:controller] = self.name.gsub(/ControllerTest$/, '').tableize
297
- end
298
- options[:controller] = options[:controller].to_s
299
- options[:action] = options[:action].to_s
300
-
301
- populated_path = path.dup
302
- options.each do |key, value|
303
- options[key] = value.to_param if value.respond_to? :to_param
304
- populated_path.gsub!(key.inspect, value.to_s)
305
- end
306
-
307
- should_name = "route #{method.to_s.upcase} #{populated_path} to/from #{options.inspect}"
308
-
309
- should should_name do
310
- assert_routing({:method => method, :path => populated_path}, options)
311
- end
312
- end
313
- end
314
- end
315
- end
316
- end