ZenTest 3.11.1 → 4.0.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/lib/test/rails.rb DELETED
@@ -1,295 +0,0 @@
1
- require 'test/unit'
2
- require 'rubygems'
3
- require 'rubygems/version'
4
- require 'test_help' # hopefully temporary, required for Test::Rails to work
5
- # until we get rid of test_help so Test::Unit::TestCase
6
- # is kept virgin.
7
- require 'rails/version' unless defined? Rails::VERSION
8
-
9
- $TESTING = true
10
-
11
- ##
12
- # = Introduction
13
- #
14
- # Test::Rails helps you build industrial-strength Rails code by:
15
- # * testing views separate from controllers
16
- # * enhancing the assertion vocabulary, and
17
- # * auditing your tests for consistency.
18
- #
19
- # = Details
20
- #
21
- # Test::Rails:
22
- # * splits Functional test into Controller and View tests.
23
- # * Splits view assertions away from controller assertions.
24
- # * Helps decouple views from controllers.
25
- # * Allows you to test AJAX actions in isolation.
26
- # * Allows you to test a single partial.
27
- # * Clearer failures when assert_tag fails.
28
- # * An auditing script analyzes missing assertions in your controllers and
29
- # views.
30
- # * Library of assertions for testing views.
31
- #
32
- # = How to Convert to Test::Rails
33
- #
34
- # You will need to make three small changes to test/test_helper.rb to set up
35
- # Test::Rails:
36
- #
37
- # First, add the following to 'test/test_helper.rb' before you require
38
- # +test_help+:
39
- #
40
- # require 'test/rails'
41
- #
42
- # Next, change the class from "Unit" to "Rails" right after you
43
- # require +test_help+.
44
- #
45
- # Your 'test/test_helper.rb' will end up looking like this:
46
- #
47
- # ENV["RAILS_ENV"] = "test"
48
- # require File.expand_path(File.dirname(__FILE__) + "/../config/environment")
49
- # require 'test/rails'
50
- # require 'test_help'
51
- #
52
- # class Test::Rails::TestCase
53
- # ...
54
- #
55
- # Finally, you need to add the extra rake tasks Test::Rails provides.
56
- # Add the following line to your Rakefile after you require
57
- # 'tasks/rails':
58
- #
59
- # require 'test/rails/rake_tasks'
60
- #
61
- # *NOTE*:
62
- #
63
- # * get/post/etc. no longer have a session or flash argument. Use the session
64
- # and flash accessor instead.
65
- # * assert_tag will (eventually) not work in controller tests.
66
- #
67
- # == Writing View Tests
68
- #
69
- # View tests live in test/views. They are named after the controller that is
70
- # being tested. For exampe, RouteViewTest will live in the file
71
- # test/views/route_view_test.rb.
72
- #
73
- # === Example View Test Case
74
- #
75
- # require 'test/test_helper'
76
- #
77
- # # We are testing RouteController's views
78
- # class RouteViewTest < Test::Rails::ViewTestCase
79
- #
80
- # fixtures :users, :routes, :points, :photos
81
- #
82
- # # testing the view for the delete action of RouteController
83
- # def test_delete
84
- # # Instance variables necessary for this view
85
- # assigns[:loggedin_user] = users(:herbert)
86
- # assigns[:route] = routes(:work)
87
- #
88
- # # render this view
89
- # render
90
- #
91
- # # assert everything is as it should be
92
- # assert_links_to "/route/flickr_refresh/#{routes(:work).id}"
93
- #
94
- # form_url = '/route/destroy'
95
- # assert_post_form form_url
96
- # assert_input form_url, :hidden, :id
97
- # assert_submit form_url, 'Delete!'
98
- # assert_links_to "/route/show/#{routes(:work).id}", 'No, I do not!'
99
- # end
100
- #
101
- # # ...
102
- #
103
- # end
104
- #
105
- # All view tests are a subclass of Test::Rails::ViewTestCase. The name of the
106
- # subclass must match the controller this view depends upon. ViewTestCase
107
- # takes care of all the setup necessary for running the tests.
108
- #
109
- # The +test_delete+ method is named after the delete method in
110
- # RouteController. The ViewTestCase#render method looks at the name of the
111
- # test and tries to figure out which view file to use, so naming tests after
112
- # actions will save you headaches and typing.
113
- #
114
- # Use +assigns+ to set up the variables the view will use when it renders.
115
- #
116
- # The call to render is the equivalent to a functional tests' get/post
117
- # methods. It makes several assumptions, so be sure to read
118
- # ViewTestCase#render carefully.
119
- #
120
- # ViewTestCase has a vastly expanded assertion library to help you out with
121
- # testing. See ViewTestCase for all the helpful assertions you can use in
122
- # your view tests.
123
- #
124
- # == Writing Controller Tests
125
- #
126
- # Controller tests are essentially functional tests without the view assertions.
127
- #
128
- # They live in test/controllers, subclass ControllerTestCase, and are
129
- # named after the controller they are testing. For example,
130
- # RouteControllerTest will live in the file
131
- # test/controllers/route_controller_test.rb.
132
- #
133
- # === Example Controller Test Case
134
- #
135
- # require 'test/test_helper'
136
- #
137
- # # We are testing RouteController's actions
138
- # class RouteControllerTest < Test::Rails::ControllerTestCase
139
- #
140
- # fixtures :users, :routes, :points, :photos
141
- #
142
- # # Testing the delete method
143
- # def test_delete
144
- # # A session accessor is provided instead of passing a hash to get.
145
- # session[:username] = users(:herbert).username
146
- #
147
- # get :delete, :id => routes(:work).id
148
- #
149
- # # assert we got a 200
150
- # assert_success
151
- #
152
- # # assert that instance variables are correctly assigned
153
- # assert_assigned :action_title, "Deleting \"#{routes(:work).name}\""
154
- # assert_assigned :route, routes(:work)
155
- # end
156
- #
157
- # # ...
158
- #
159
- # end
160
- #
161
- # == Writing Abstract Test Cases
162
- #
163
- # Abstract test cases are a great way to refactor your tests and
164
- # ensure you do not violate the DRY principal and share code between
165
- # different test classes. If you have common setup code for your test
166
- # classes you can create your own subclass of ControllerTestCase or
167
- # ViewTestCase.
168
- #
169
- # === Example Abstract Test Case
170
- #
171
- # class RobotControllerTestCase < Test::Rails::ControllerTestCase
172
- #
173
- # fixtures :markets, :people
174
- #
175
- # def setup
176
- # super
177
- #
178
- # # We're running tests in this class so we don't need to do any more
179
- # # setup
180
- # return if self.class == RobotControllerTestCase
181
- #
182
- # # Set our current host
183
- # @host = 'www.test.robotcoop.com'
184
- # util_set_host @host
185
- # end
186
- #
187
- # ##
188
- # # Sets the hostname to +host+ for this request.
189
- #
190
- # def util_set_host(hoston)
191
- # @request.host = host
192
- # end
193
- #
194
- # end
195
- #
196
- # = How to Audit Your Tests
197
- #
198
- # <tt>bin/rails_test_audit</tt> ensures that your view tests'
199
- # +assign+s are compared against your controller tests'
200
- # assert_assigned, warning you when you've forgotten to test
201
- # something.
202
- #
203
- # Given:
204
- #
205
- # class RouteControllerTest < Test::Rails::ControllerTestCase
206
- # def test_flickr_refresh
207
- # get :flickr_refresh, :id => routes(:work).id
208
- # assert_success
209
- #
210
- # assert_assigned :tz_name, 'Pacific Time (US & Canada)'
211
- # end
212
- # end
213
- #
214
- # And:
215
- #
216
- # class RouteViewTest < Test::Rails::ViewTestCase
217
- # def test_flickr_refresh
218
- # assigns[:route] = routes(:work)
219
- # assigns[:tz_name] = 'Pacific Time (US & Canada)'
220
- #
221
- # render
222
- #
223
- # # ...
224
- # end
225
- # end
226
- #
227
- # +rails_test_audit+ will see that you don't have an +assert_assigned+
228
- # for +route+ and will output:
229
- #
230
- # require 'test/test_helper'
231
- #
232
- # class RouteControllerTest < Test::Rails::ControllerTestCase
233
- #
234
- # def test_flickr_refresh
235
- # assert_assigned :route, routes(:work)
236
- # end
237
- #
238
- # end
239
- #
240
- # = How 'rake test' Changed
241
- #
242
- # test:views and test:controllers targets get added so you can run just the
243
- # view or controller tests.
244
- #
245
- # The "test" target runs tests in the following order: units, controllers,
246
- # views, functionals, integration.
247
- #
248
- # The test target no longer runs all tests, it stops on the first
249
- # failure. This way a failure in a unit test doesn't fill your screen
250
- # with less important errors because the underlying failure also
251
- # affected your controllers and views.
252
- #
253
- # The stats target is updated to account for controller and view tests.
254
-
255
- module Test::Rails
256
-
257
- @rails_version = Gem::Version.new Rails::VERSION::STRING
258
- @v1_2 = Gem::Version.new '1.2'
259
-
260
- ##
261
- # The currently loaded rails version. Better than Rails::VERSION::STRING
262
- # since this one is comparable.
263
-
264
- def self.rails_version
265
- @rails_version
266
- end
267
-
268
- def self.v1_2 # :nodoc:
269
- @v1_2
270
- end
271
-
272
- end
273
-
274
- class Object # :nodoc:
275
- def self.path2class(klassname)
276
- klassname.split('::').inject(Object) { |k,n| k.const_get n }
277
- end
278
- end
279
-
280
- require 'test/zentest_assertions'
281
- require 'test/rails/test_case'
282
- require 'test/rails/functional_test_case'
283
- require 'test/rails/controller_test_case'
284
- require 'test/rails/helper_test_case'
285
- require 'test/rails/ivar_proxy'
286
- require 'test/rails/view_test_case'
287
-
288
- ##
289
- # Use sensible defaults.
290
-
291
- class Test::Unit::TestCase # :nodoc:
292
- self.use_transactional_fixtures = true
293
- self.use_instantiated_fixtures = false
294
- end
295
-
@@ -1,382 +0,0 @@
1
- ##
2
- # ControllerTestCase allows controllers to be tested independent of their
3
- # views.
4
- #
5
- # = Features
6
- #
7
- # * ActionMailer is already set up for you.
8
- # * The session and flash accessors work on both sides of get/post/etc.
9
- # * Optional automatic auditing for missing assert_assigns. See
10
- # util_audit_assert_assigned
11
- #
12
- # = Naming
13
- #
14
- # The test class must be named after your controller class name, so if
15
- # you're testing actions for the +RouteController+ you would name your
16
- # test case +RouteControllerTest+.
17
- #
18
- # The test names should be in the form of +test_action_edgecase+ where
19
- # 'action' corresponds to the name of the controller action, and
20
- # 'edgecase' describes the scenario you are testing.
21
- #
22
- # If you are testing an action named 'show' your test should be named
23
- # +test_show+. If your action behaves differently depending upon its
24
- # arguments then you can make the test name descriptive like
25
- # +test_show_photos+ and +test_show_no_photos+.
26
- #
27
- # = Examples
28
- #
29
- # == Typical Controller Test
30
- #
31
- # class RouteControllerTest < Test::Rails::ControllerTestCase
32
- #
33
- # fixtures :users, :routes, :points, :photos
34
- #
35
- # def test_delete
36
- # # Store current count
37
- # count = Route.count
38
- # # Set up our environment
39
- # session[:username] = users(:herbert).username
40
- #
41
- # # perform the delete action
42
- # get :delete, :id => routes(:work).id
43
- #
44
- # # Assert we got a 200
45
- # assert_response :success
46
- # # Assert controller deleted route
47
- # assert_equal count-1, Route.count
48
- # # Ensure that @action_title is set properly
49
- # assert_assigned :action_title, "Deleting \"#{routes(:work).name}\""
50
- # # Ensure that @route is set properly
51
- # assert_assigned :route, routes(:work)
52
- # end
53
- #
54
- # end
55
- #
56
- # == ActionMailer Test
57
- #
58
- # class ApplicationController < ActionController::Base
59
- #
60
- # ##
61
- # # Send an email when we get an unhandled exception.
62
- #
63
- # def log_error(exception)
64
- # case exception
65
- # when ::ActionController::RoutingError,
66
- # ::ActionController::UnknownAction,
67
- # ::ActiveRecord::RecordNotFound then
68
- # # ignore
69
- # else
70
- # unless RAILS_ENV == 'development' then
71
- # Email.deliver_error exception, params, session, @request.env
72
- # end
73
- # end
74
- # end
75
- #
76
- # end
77
- #
78
- # ##
79
- # # Dummy Controller just for testing.
80
- #
81
- # class DummyController < ApplicationController
82
- #
83
- # def error
84
- # # Simulate a bug in our application
85
- # raise RuntimeError
86
- # end
87
- #
88
- # end
89
- #
90
- # class DummyControllerTest < Test::Rails::ControllerTestCase
91
- #
92
- # def test_error_email
93
- # # The rescue_action added by ControllerTestCase needs to be removed so
94
- # # that exceptions fall through to the real error handler
95
- # @controller.class.send :remove_method, :rescue_action
96
- #
97
- # # Fire off a request
98
- # get :error
99
- #
100
- # # We should get a 500
101
- # assert_response 500
102
- #
103
- # # And one delivered email
104
- # assert_equal 1, @deliveries.length, 'error email sent'
105
- # end
106
- #
107
- # end
108
- #
109
- #--
110
- # TODO: Ensure that assert_tag doesn't work
111
- # TODO: Cookie input.
112
-
113
- class Test::Rails::ControllerTestCase < Test::Rails::FunctionalTestCase
114
-
115
- self.use_transactional_fixtures = true
116
- self.use_instantiated_fixtures = false
117
-
118
- NOTHING = Object.new # :nodoc:
119
-
120
- DEFAULT_ASSIGNS = %w[
121
- _cookies _flash _headers _params _request _response _session
122
-
123
- cookies flash headers params request response session
124
-
125
- action_name
126
- before_filter_chain_aborted
127
- db_rt_after_render
128
- db_rt_before_render
129
- ignore_missing_templates
130
- loggedin_user
131
- logger
132
- rendering_runtime
133
- request_origin
134
- template
135
- template_class
136
- template_root
137
- url
138
- user
139
- variables_added
140
- ]
141
-
142
- def setup
143
- return if self.class == Test::Rails::ControllerTestCase
144
-
145
- @controller_class_name ||= self.class.name.sub 'Test', ''
146
-
147
- super
148
-
149
- @controller_class.send(:define_method, :rescue_action) { |e| raise e }
150
-
151
- @deliveries = []
152
- ActionMailer::Base.deliveries = @deliveries
153
-
154
- # used by util_audit_assert_assigns
155
- @assigns_asserted = []
156
- @assigns_ignored ||= [] # untested assigns to ignore
157
- end
158
-
159
- ##
160
- # Excutes the request +action+ with +params+.
161
- #
162
- # See also: get, post, put, delete, head, xml_http_request
163
-
164
- def process(action, parameters = nil)
165
- parameters ||= {}
166
-
167
- @request.recycle!
168
- @request.env['REQUEST_METHOD'] ||= 'GET'
169
- @request.action = action.to_s
170
-
171
- @request.assign_parameters @controller_class.controller_path, action.to_s,
172
- parameters
173
-
174
- build_request_uri action, parameters
175
-
176
- @controller.process @request, @response
177
- end
178
-
179
- ##
180
- # Performs a GET request on +action+ with +params+.
181
-
182
- def get(action, parameters = nil)
183
- @request.env['REQUEST_METHOD'] = 'GET'
184
- process action, parameters
185
- end
186
-
187
- ##
188
- # Performs a HEAD request on +action+ with +params+.
189
-
190
- def head(action, parameters = nil)
191
- @request.env['REQUEST_METHOD'] = 'HEAD'
192
- process action, parameters
193
- end
194
-
195
- ##
196
- # Performs a POST request on +action+ with +params+.
197
-
198
- def post(action, parameters = nil)
199
- @request.env['REQUEST_METHOD'] = 'POST'
200
- process action, parameters
201
- end
202
-
203
- ##
204
- # Performs a PUT request on +action+ with +params+.
205
-
206
- def put(action, parameters = nil)
207
- @request.env['REQUEST_METHOD'] = 'PUT'
208
- process action, parameters
209
- end
210
-
211
- ##
212
- # Performs a DELETE request on +action+ with +params+.
213
-
214
- def delete(action, parameters = nil)
215
- @request.env['REQUEST_METHOD'] = 'DELETE'
216
- process action, parameters
217
- end
218
-
219
- ##
220
- # Performs a XMLHttpRequest request using +request_method+ on +action+ with
221
- # +params+.
222
-
223
- def xml_http_request(request_method, action, parameters = nil)
224
- @request.env['REQUEST_METHOD'] = request_method.to_s
225
-
226
- @request.env['HTTP_X_REQUESTED_WITH'] = 'XMLHttpRequest'
227
- @request.env['HTTP_ACCEPT'] = 'text/javascript, text/html, application/xml, text/xml, */*'
228
-
229
- result = process action, parameters
230
-
231
- @request.env.delete 'HTTP_X_REQUESTED_WITH'
232
- @request.env.delete 'HTTP_ACCEPT'
233
-
234
- return result
235
- end
236
-
237
- ##
238
- # Friendly alias for xml_http_request
239
-
240
- alias xhr xml_http_request
241
-
242
- ##
243
- # Asserts that the assigns variable +ivar+ is assigned to +value+. If
244
- # +value+ is omitted, asserts that assigns variable +ivar+ exists.
245
-
246
- def assert_assigned(ivar, value = NOTHING)
247
- ivar = ivar.to_s
248
- @assigns_asserted << ivar
249
- assert_includes assigns, ivar, "#{ivar.inspect} missing from assigns"
250
- unless value.equal? NOTHING then
251
- assert_equal value, assigns[ivar],
252
- "assert_assigned #{ivar.intern.inspect}"
253
- end
254
- end
255
-
256
- ##
257
- # Asserts the response content type matches +type+.
258
-
259
- def assert_content_type(type, message = nil)
260
- assert_equal type, @response.headers['Content-Type'], message
261
- end
262
-
263
- ##
264
- # Asserts that +key+ of flash has +content+. If +content+ is a Regexp, then
265
- # the assertion will fail if the Regexp does not match.
266
- #
267
- # controller:
268
- # flash[:notice] = 'Please log in'
269
- #
270
- # test:
271
- # assert_flash :notice, 'Please log in'
272
-
273
- def assert_flash(key, content)
274
- assert flash.include?(key),
275
- "#{key.inspect} missing from flash, has #{flash.keys.inspect}"
276
-
277
- case content
278
- when Regexp then
279
- assert_match content, flash[key],
280
- "Content of flash[#{key.inspect}] did not match"
281
- else
282
- assert_equal content, flash[key],
283
- "Incorrect content in flash[#{key.inspect}]"
284
- end
285
- end
286
-
287
- ##
288
- # Asserts that the assigns variable +ivar+ is not set.
289
-
290
- def deny_assigned(ivar)
291
- ivar = ivar.to_s
292
- deny_includes assigns, ivar
293
- end
294
-
295
- ##
296
- # Checks your assert_assigned tests against the instance variables in
297
- # assigns. Fails if the two don't match.
298
- #
299
- # Add util_audit_assert_assigned to your teardown. If you have instance
300
- # variables that you don't need to set (for example, were set in a
301
- # before_filter in ApplicationController) then add them to the
302
- # @assigns_ignored instance variable in your setup.
303
- #
304
- # = Example
305
- #
306
- # == Controller method
307
- #
308
- # class UserController < ApplicationController
309
- # def new
310
- # # ...
311
- #
312
- # @login_form = false
313
- # end
314
- # end
315
- #
316
- # == Test setup:
317
- #
318
- # class UserControllerTest < Test::Rails::ControllerTestCase
319
- #
320
- # def teardown
321
- # super
322
- # util_audit_assert_assigned
323
- # end
324
- #
325
- # def test_new
326
- # get :new
327
- #
328
- # assert_response :success
329
- # # no assert_assigns for @login_form
330
- # end
331
- #
332
- # end
333
- #
334
- # == Output
335
- # 1) Failure:
336
- # test_new(UserControllerTest)
337
- # [[...]/controller_test_case.rb:331:in `util_audit_assert_assigned'
338
- # [...]/user_controller_test.rb:14:in `teardown_without_fixtures'
339
- # [...]fixtures.rb:555:in `teardown']:
340
- # You are missing these assert_assigned assertions:
341
- # assert_assigned :login_form #, some_value
342
- # .
343
-
344
- def util_audit_assert_assigned
345
- return unless @test_passed
346
- return unless @controller.send :performed?
347
- all_assigns = assigns.keys.sort
348
-
349
- assigns_ignored = DEFAULT_ASSIGNS | @assigns_ignored
350
- assigns_ignored = assigns_ignored.map { |a| a.to_s }
351
-
352
- assigns_created = all_assigns - assigns_ignored
353
- assigns_asserted = @assigns_asserted - assigns_ignored
354
-
355
- assigns_missing = assigns_created - assigns_asserted
356
-
357
- return if assigns_missing.empty?
358
-
359
- message = []
360
- message << "You are missing these assert_assigned assertions:"
361
- assigns_missing.sort.each do |ivar|
362
- message << " assert_assigned #{ivar.intern.inspect} #, :some_value"
363
- end
364
- message << nil # stupid '.'
365
-
366
- flunk message.join("\n")
367
- end
368
-
369
- private
370
-
371
- def build_request_uri(action, parameters)
372
- return if @request.env['REQUEST_URI']
373
-
374
- options = @controller.send :rewrite_options, parameters
375
- options.update :only_path => true, :action => action
376
-
377
- url = ActionController::UrlRewriter.new @request, parameters
378
- @request.set_REQUEST_URI url.rewrite(options)
379
- end
380
-
381
- end
382
-