responders 1.1.2 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,55 +1,53 @@
1
1
  <% module_namespacing do -%>
2
2
  class <%= controller_class_name %>Controller < ApplicationController
3
- <%= controller_before_filter %> :set_<%= singular_table_name %>, only: [:show, :edit, :update, :destroy]
4
-
5
- respond_to :html
3
+ <%= controller_before_filter %> :set_<%= file_name %>, only: [:show, :edit, :update, :destroy]
6
4
 
7
5
  <% unless options[:singleton] -%>
8
6
  def index
9
- @<%= plural_table_name %> = <%= orm_class.all(class_name) %>
10
- respond_with(@<%= plural_table_name %>)
7
+ @<%= table_name %> = <%= orm_class.all(class_name) %>
8
+ respond_with(@<%= table_name %>)
11
9
  end
12
10
  <% end -%>
13
11
 
14
12
  def show
15
- respond_with(@<%= singular_table_name %>)
13
+ respond_with(@<%= file_name %>)
16
14
  end
17
15
 
18
16
  def new
19
- @<%= singular_table_name %> = <%= orm_class.build(class_name) %>
20
- respond_with(@<%= singular_table_name %>)
17
+ @<%= file_name %> = <%= orm_class.build(class_name) %>
18
+ respond_with(@<%= file_name %>)
21
19
  end
22
20
 
23
21
  def edit
24
22
  end
25
23
 
26
24
  def create
27
- @<%= singular_table_name %> = <%= orm_class.build(class_name, attributes_params) %>
25
+ @<%= file_name %> = <%= orm_class.build(class_name, attributes_params) %>
28
26
  <%= "flash[:notice] = '#{class_name} was successfully created.' if " if flash? %>@<%= orm_instance.save %>
29
- respond_with(@<%= singular_table_name %>)
27
+ respond_with(@<%= file_name %>)
30
28
  end
31
29
 
32
30
  def update
33
31
  <%= "flash[:notice] = '#{class_name} was successfully updated.' if " if flash? %>@<%= orm_instance_update(attributes_params) %>
34
- respond_with(@<%= singular_table_name %>)
32
+ respond_with(@<%= file_name %>)
35
33
  end
36
34
 
37
35
  def destroy
38
36
  @<%= orm_instance.destroy %>
39
- respond_with(@<%= singular_table_name %>)
37
+ respond_with(@<%= file_name %>)
40
38
  end
41
39
 
42
40
  private
43
- def set_<%= singular_table_name %>
44
- @<%= singular_table_name %> = <%= orm_class.find(class_name, "params[:id]") %>
41
+ def set_<%= file_name %>
42
+ @<%= file_name %> = <%= orm_class.find(class_name, "params[:id]") %>
45
43
  end
46
44
  <%- if strong_parameters_defined? -%>
47
45
 
48
- def <%= "#{singular_table_name}_params" %>
46
+ def <%= "#{file_name}_params" %>
49
47
  <%- if attributes_names.empty? -%>
50
- params[:<%= singular_table_name %>]
48
+ params[:<%= file_name %>]
51
49
  <%- else -%>
52
- params.require(:<%= singular_table_name %>).permit(<%= attributes_names.map { |name| ":#{name}" }.join(', ') %>)
50
+ params.require(:<%= file_name %>).permit(<%= attributes_names.map { |name| ":#{name}" }.join(', ') %>)
53
51
  <%- end -%>
54
52
  end
55
53
  <%- end -%>
@@ -14,10 +14,6 @@ class ApplicationResponder < ActionController::Responder
14
14
  # Redirects resources to the collection path (index action) instead
15
15
  # of the resource path (show action) for POST/PUT/DELETE requests.
16
16
  # include Responders::CollectionResponder
17
-
18
- # Allows to use a callable object as the redirect location with respond_with,
19
- # eg a route that requires persisted objects when the validation may fail.
20
- # include Responders::LocationResponder
21
17
  end
22
18
  RUBY
23
19
  end
data/lib/responders.rb CHANGED
@@ -1,4 +1,9 @@
1
- require 'action_controller'
1
+ require 'action_controller/base'
2
+
3
+ module ActionController
4
+ autoload :Responder, 'action_controller/responder'
5
+ autoload :RespondWith, 'action_controller/respond_with'
6
+ end
2
7
 
3
8
  module Responders
4
9
  autoload :FlashResponder, 'responders/flash_responder'
@@ -10,7 +15,7 @@ module Responders
10
15
 
11
16
  class Railtie < ::Rails::Railtie
12
17
  config.responders = ActiveSupport::OrderedOptions.new
13
- config.responders.flash_keys = [ :notice, :alert ]
18
+ config.responders.flash_keys = [:notice, :alert]
14
19
  config.responders.namespace_lookup = false
15
20
 
16
21
  if config.respond_to?(:app_generators)
@@ -29,3 +34,7 @@ module Responders
29
34
  end
30
35
  end
31
36
  end
37
+
38
+ ActiveSupport.on_load(:action_controller) do
39
+ include ActionController::RespondWith
40
+ end
@@ -1,26 +1,8 @@
1
1
  module Responders
2
- # Responder to accept callable objects as the redirect location.
3
- # Useful when you want to use the <tt>respond_with</tt> method with
4
- # a route that requires persisted objects, but the validation may fail.
5
- #
6
- # class ThingsController < ApplicationController
7
- # responders :location, :flash
8
- # respond_to :html
9
- #
10
- # def create
11
- # @thing = Things.create(params[:thing])
12
- # respond_with @thing, location: -> { thing_path(@thing) }
13
- # end
14
- # end
15
- #
16
2
  module LocationResponder
17
- def initialize(controller, resources, options = {})
18
- super
19
-
20
- if options[:location].respond_to?(:call)
21
- location = options.delete(:location)
22
- options[:location] = location.call unless has_errors?
23
- end
3
+ def self.included(_base)
4
+ ActiveSupport::Deprecation.warn "Responders::LocationResponder is enabled by default, "
5
+ "no need to include it", caller
24
6
  end
25
7
  end
26
8
  end
@@ -1,3 +1,3 @@
1
1
  module Responders
2
- VERSION = "1.1.2".freeze
2
+ VERSION = "2.0.0".freeze
3
3
  end
@@ -0,0 +1,717 @@
1
+ require 'test_helper'
2
+
3
+ class Customer < Struct.new(:name, :id)
4
+ extend ActiveModel::Naming
5
+ include ActiveModel::Conversion
6
+
7
+ undef_method :to_json
8
+
9
+ def to_xml(options={})
10
+ if options[:builder]
11
+ options[:builder].name name
12
+ else
13
+ "<name>#{name}</name>"
14
+ end
15
+ end
16
+
17
+ def to_js(options={})
18
+ "name: #{name.inspect}"
19
+ end
20
+ alias :to_text :to_js
21
+
22
+ def errors
23
+ []
24
+ end
25
+
26
+ def persisted?
27
+ id.present?
28
+ end
29
+ end
30
+
31
+ class ValidatedCustomer < Customer
32
+ def errors
33
+ if name =~ /Sikachu/i
34
+ []
35
+ else
36
+ [{:name => "is invalid"}]
37
+ end
38
+ end
39
+ end
40
+
41
+ module Quiz
42
+ class Question < Struct.new(:name, :id)
43
+ extend ActiveModel::Naming
44
+ include ActiveModel::Conversion
45
+
46
+ def persisted?
47
+ id.present?
48
+ end
49
+ end
50
+
51
+ class Store < Question
52
+ end
53
+ end
54
+
55
+ class RespondWithController < ApplicationController
56
+ class CustomerWithJson < Customer
57
+ def to_json; super; end
58
+ end
59
+
60
+ respond_to :html, :json, :touch
61
+ respond_to :xml, :except => :using_resource_with_block
62
+ respond_to :js, :only => [ :using_resource_with_block, :using_resource, 'using_hash_resource' ]
63
+
64
+ def using_resource
65
+ respond_with(resource)
66
+ end
67
+
68
+ def using_hash_resource
69
+ respond_with({:result => resource})
70
+ end
71
+
72
+ def using_resource_with_block
73
+ respond_with(resource) do |format|
74
+ format.csv { render :text => "CSV" }
75
+ end
76
+ end
77
+
78
+ def using_resource_with_overwrite_block
79
+ respond_with(resource) do |format|
80
+ format.html { render :text => "HTML" }
81
+ end
82
+ end
83
+
84
+ def using_resource_with_collection
85
+ respond_with([resource, Customer.new("jamis", 9)])
86
+ end
87
+
88
+ def using_resource_with_parent
89
+ respond_with(Quiz::Store.new("developer?", 11), Customer.new("david", 13))
90
+ end
91
+
92
+ def using_resource_with_status_and_location
93
+ respond_with(resource, :location => "http://test.host/", :status => :created)
94
+ end
95
+
96
+ def using_resource_with_json
97
+ respond_with(CustomerWithJson.new("david", request.delete? ? nil : 13))
98
+ end
99
+
100
+ def using_invalid_resource_with_template
101
+ respond_with(resource)
102
+ end
103
+
104
+ def using_options_with_template
105
+ @customer = resource
106
+ respond_with(@customer, :status => 123, :location => "http://test.host/")
107
+ end
108
+
109
+ def using_resource_with_responder
110
+ responder = proc { |c, r, o| c.render :text => "Resource name is #{r.first.name}" }
111
+ respond_with(resource, :responder => responder)
112
+ end
113
+
114
+ def using_resource_with_action
115
+ respond_with(resource, :action => :foo) do |format|
116
+ format.html { raise ActionView::MissingTemplate.new([], "bar", ["foo"], {}, false) }
117
+ end
118
+ end
119
+
120
+ def using_responder_with_respond
121
+ responder = Class.new(ActionController::Responder) do
122
+ def respond; @controller.render :text => "respond #{format}"; end
123
+ end
124
+ respond_with(resource, :responder => responder)
125
+ end
126
+
127
+ def respond_with_additional_params
128
+ @params = RespondWithController.params
129
+ respond_with({:result => resource}, @params)
130
+ end
131
+
132
+ protected
133
+ def self.params
134
+ {
135
+ :foo => 'bar'
136
+ }
137
+ end
138
+
139
+ def resource
140
+ Customer.new("david", request.delete? ? nil : 13)
141
+ end
142
+ end
143
+
144
+ class InheritedRespondWithController < RespondWithController
145
+ clear_respond_to
146
+ respond_to :xml, :json
147
+
148
+ def index
149
+ respond_with(resource) do |format|
150
+ format.json { render :text => "JSON" }
151
+ end
152
+ end
153
+ end
154
+
155
+ class CsvRespondWithController < ApplicationController
156
+ respond_to :csv
157
+
158
+ class RespondWithCsv
159
+ def to_csv
160
+ "c,s,v"
161
+ end
162
+ end
163
+
164
+ def index
165
+ respond_with(RespondWithCsv.new)
166
+ end
167
+ end
168
+
169
+ class EmptyRespondWithController < ApplicationController
170
+ clear_respond_to
171
+ def index
172
+ respond_with(Customer.new("david", 13))
173
+ end
174
+ end
175
+
176
+ class RespondWithControllerTest < ActionController::TestCase
177
+ def setup
178
+ super
179
+ @request.host = "www.example.com"
180
+ Mime::Type.register_alias('text/html', :iphone)
181
+ Mime::Type.register_alias('text/html', :touch)
182
+ Mime::Type.register('text/x-mobile', :mobile)
183
+ end
184
+
185
+ def teardown
186
+ super
187
+ Mime::Type.unregister(:iphone)
188
+ Mime::Type.unregister(:touch)
189
+ Mime::Type.unregister(:mobile)
190
+ end
191
+
192
+ def test_respond_with_shouldnt_modify_original_hash
193
+ get :respond_with_additional_params
194
+ assert_equal RespondWithController.params, assigns(:params)
195
+ end
196
+
197
+ def test_using_resource
198
+ @request.accept = "application/xml"
199
+ get :using_resource
200
+ assert_equal "application/xml", @response.content_type
201
+ assert_equal "<name>david</name>", @response.body
202
+
203
+ @request.accept = "application/json"
204
+ assert_raise ActionView::MissingTemplate do
205
+ get :using_resource
206
+ end
207
+ end
208
+
209
+ def test_using_resource_with_js_simply_tries_to_render_the_template
210
+ @request.accept = "text/javascript"
211
+ get :using_resource
212
+ assert_equal "text/javascript", @response.content_type
213
+ assert_equal "alert(\"Hi\");", @response.body
214
+ end
215
+
216
+ def test_using_hash_resource_with_js_raises_an_error_if_template_cant_be_found
217
+ @request.accept = "text/javascript"
218
+ assert_raise ActionView::MissingTemplate do
219
+ get :using_hash_resource
220
+ end
221
+ end
222
+
223
+ def test_using_hash_resource
224
+ @request.accept = "application/xml"
225
+ get :using_hash_resource
226
+ assert_equal "application/xml", @response.content_type
227
+ assert_equal "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<hash>\n <name>david</name>\n</hash>\n", @response.body
228
+
229
+ @request.accept = "application/json"
230
+ get :using_hash_resource
231
+ assert_equal "application/json", @response.content_type
232
+ assert @response.body.include?("result")
233
+ assert @response.body.include?('"name":"david"')
234
+ assert @response.body.include?('"id":13')
235
+ end
236
+
237
+ def test_using_hash_resource_with_post
238
+ @request.accept = "application/json"
239
+ assert_raise ArgumentError, "Nil location provided. Can't build URI." do
240
+ post :using_hash_resource
241
+ end
242
+ end
243
+
244
+ def test_using_resource_with_block
245
+ @request.accept = "*/*"
246
+ get :using_resource_with_block
247
+ assert_equal "text/html", @response.content_type
248
+ assert_equal 'Hello world!', @response.body
249
+
250
+ @request.accept = "text/csv"
251
+ get :using_resource_with_block
252
+ assert_equal "text/csv", @response.content_type
253
+ assert_equal "CSV", @response.body
254
+
255
+ @request.accept = "application/xml"
256
+ get :using_resource
257
+ assert_equal "application/xml", @response.content_type
258
+ assert_equal "<name>david</name>", @response.body
259
+ end
260
+
261
+ def test_using_resource_with_overwrite_block
262
+ get :using_resource_with_overwrite_block
263
+ assert_equal "text/html", @response.content_type
264
+ assert_equal "HTML", @response.body
265
+ end
266
+
267
+ def test_not_acceptable
268
+ @request.accept = "application/xml"
269
+ assert_raises(ActionController::UnknownFormat) do
270
+ get :using_resource_with_block
271
+ end
272
+
273
+ @request.accept = "text/javascript"
274
+ assert_raises(ActionController::UnknownFormat) do
275
+ get :using_resource_with_overwrite_block
276
+ end
277
+ end
278
+
279
+ def test_using_resource_for_post_with_html_redirects_on_success
280
+ with_test_route_set do
281
+ post :using_resource
282
+ assert_equal "text/html", @response.content_type
283
+ assert_equal 302, @response.status
284
+ assert_equal "http://www.example.com/customers/13", @response.location
285
+ assert @response.redirect?
286
+ end
287
+ end
288
+
289
+ def test_using_resource_for_post_with_html_rerender_on_failure
290
+ with_test_route_set do
291
+ errors = { :name => :invalid }
292
+ Customer.any_instance.stubs(:errors).returns(errors)
293
+ post :using_resource
294
+ assert_equal "text/html", @response.content_type
295
+ assert_equal 200, @response.status
296
+ assert_equal "New world!\n", @response.body
297
+ assert_nil @response.location
298
+ end
299
+ end
300
+
301
+ def test_using_resource_for_post_with_xml_yields_created_on_success
302
+ with_test_route_set do
303
+ @request.accept = "application/xml"
304
+ post :using_resource
305
+ assert_equal "application/xml", @response.content_type
306
+ assert_equal 201, @response.status
307
+ assert_equal "<name>david</name>", @response.body
308
+ assert_equal "http://www.example.com/customers/13", @response.location
309
+ end
310
+ end
311
+
312
+ def test_using_resource_for_post_with_xml_yields_unprocessable_entity_on_failure
313
+ with_test_route_set do
314
+ @request.accept = "application/xml"
315
+ errors = { :name => :invalid }
316
+ Customer.any_instance.stubs(:errors).returns(errors)
317
+ post :using_resource
318
+ assert_equal "application/xml", @response.content_type
319
+ assert_equal 422, @response.status
320
+ assert_equal errors.to_xml, @response.body
321
+ assert_nil @response.location
322
+ end
323
+ end
324
+
325
+ def test_using_resource_for_post_with_json_yields_unprocessable_entity_on_failure
326
+ with_test_route_set do
327
+ @request.accept = "application/json"
328
+ errors = { :name => :invalid }
329
+ Customer.any_instance.stubs(:errors).returns(errors)
330
+ post :using_resource
331
+ assert_equal "application/json", @response.content_type
332
+ assert_equal 422, @response.status
333
+ errors = {:errors => errors}
334
+ assert_equal errors.to_json, @response.body
335
+ assert_nil @response.location
336
+ end
337
+ end
338
+
339
+ def test_using_resource_for_patch_with_html_redirects_on_success
340
+ with_test_route_set do
341
+ patch :using_resource
342
+ assert_equal "text/html", @response.content_type
343
+ assert_equal 302, @response.status
344
+ assert_equal "http://www.example.com/customers/13", @response.location
345
+ assert @response.redirect?
346
+ end
347
+ end
348
+
349
+ def test_using_resource_for_patch_with_html_rerender_on_failure
350
+ with_test_route_set do
351
+ errors = { :name => :invalid }
352
+ Customer.any_instance.stubs(:errors).returns(errors)
353
+ patch :using_resource
354
+ assert_equal "text/html", @response.content_type
355
+ assert_equal 200, @response.status
356
+ assert_equal "Edit world!\n", @response.body
357
+ assert_nil @response.location
358
+ end
359
+ end
360
+
361
+ def test_using_resource_for_patch_with_html_rerender_on_failure_even_on_method_override
362
+ with_test_route_set do
363
+ errors = { :name => :invalid }
364
+ Customer.any_instance.stubs(:errors).returns(errors)
365
+ @request.env["rack.methodoverride.original_method"] = "POST"
366
+ patch :using_resource
367
+ assert_equal "text/html", @response.content_type
368
+ assert_equal 200, @response.status
369
+ assert_equal "Edit world!\n", @response.body
370
+ assert_nil @response.location
371
+ end
372
+ end
373
+
374
+ def test_using_resource_for_put_with_html_redirects_on_success
375
+ with_test_route_set do
376
+ put :using_resource
377
+ assert_equal "text/html", @response.content_type
378
+ assert_equal 302, @response.status
379
+ assert_equal "http://www.example.com/customers/13", @response.location
380
+ assert @response.redirect?
381
+ end
382
+ end
383
+
384
+ def test_using_resource_for_put_with_html_rerender_on_failure
385
+ with_test_route_set do
386
+ errors = { :name => :invalid }
387
+ Customer.any_instance.stubs(:errors).returns(errors)
388
+ put :using_resource
389
+
390
+ assert_equal "text/html", @response.content_type
391
+ assert_equal 200, @response.status
392
+ assert_equal "Edit world!\n", @response.body
393
+ assert_nil @response.location
394
+ end
395
+ end
396
+
397
+ def test_using_resource_for_put_with_html_rerender_on_failure_even_on_method_override
398
+ with_test_route_set do
399
+ errors = { :name => :invalid }
400
+ Customer.any_instance.stubs(:errors).returns(errors)
401
+ @request.env["rack.methodoverride.original_method"] = "POST"
402
+ put :using_resource
403
+ assert_equal "text/html", @response.content_type
404
+ assert_equal 200, @response.status
405
+ assert_equal "Edit world!\n", @response.body
406
+ assert_nil @response.location
407
+ end
408
+ end
409
+
410
+ def test_using_resource_for_put_with_xml_yields_no_content_on_success
411
+ @request.accept = "application/xml"
412
+ put :using_resource
413
+ assert_equal "application/xml", @response.content_type
414
+ assert_equal 204, @response.status
415
+ assert_equal "", @response.body
416
+ end
417
+
418
+ def test_using_resource_for_put_with_json_yields_no_content_on_success
419
+ @request.accept = "application/json"
420
+ put :using_resource_with_json
421
+ assert_equal "application/json", @response.content_type
422
+ assert_equal 204, @response.status
423
+ assert_equal "", @response.body
424
+ end
425
+
426
+ def test_using_resource_for_put_with_xml_yields_unprocessable_entity_on_failure
427
+ @request.accept = "application/xml"
428
+ errors = { :name => :invalid }
429
+ Customer.any_instance.stubs(:errors).returns(errors)
430
+ put :using_resource
431
+ assert_equal "application/xml", @response.content_type
432
+ assert_equal 422, @response.status
433
+ assert_equal errors.to_xml, @response.body
434
+ assert_nil @response.location
435
+ end
436
+
437
+ def test_using_resource_for_put_with_json_yields_unprocessable_entity_on_failure
438
+ @request.accept = "application/json"
439
+ errors = { :name => :invalid }
440
+ Customer.any_instance.stubs(:errors).returns(errors)
441
+ put :using_resource
442
+ assert_equal "application/json", @response.content_type
443
+ assert_equal 422, @response.status
444
+ errors = {:errors => errors}
445
+ assert_equal errors.to_json, @response.body
446
+ assert_nil @response.location
447
+ end
448
+
449
+ def test_using_resource_for_delete_with_html_redirects_on_success
450
+ with_test_route_set do
451
+ Customer.any_instance.stubs(:destroyed?).returns(true)
452
+ delete :using_resource
453
+ assert_equal "text/html", @response.content_type
454
+ assert_equal 302, @response.status
455
+ assert_equal "http://www.example.com/customers", @response.location
456
+ end
457
+ end
458
+
459
+ def test_using_resource_for_delete_with_xml_yields_no_content_on_success
460
+ Customer.any_instance.stubs(:destroyed?).returns(true)
461
+ @request.accept = "application/xml"
462
+ delete :using_resource
463
+ assert_equal "application/xml", @response.content_type
464
+ assert_equal 204, @response.status
465
+ assert_equal "", @response.body
466
+ end
467
+
468
+ def test_using_resource_for_delete_with_json_yields_no_content_on_success
469
+ Customer.any_instance.stubs(:destroyed?).returns(true)
470
+ @request.accept = "application/json"
471
+ delete :using_resource_with_json
472
+ assert_equal "application/json", @response.content_type
473
+ assert_equal 204, @response.status
474
+ assert_equal "", @response.body
475
+ end
476
+
477
+ def test_using_resource_for_delete_with_html_redirects_on_failure
478
+ with_test_route_set do
479
+ errors = { :name => :invalid }
480
+ Customer.any_instance.stubs(:errors).returns(errors)
481
+ Customer.any_instance.stubs(:destroyed?).returns(false)
482
+ delete :using_resource
483
+ assert_equal "text/html", @response.content_type
484
+ assert_equal 302, @response.status
485
+ assert_equal "http://www.example.com/customers", @response.location
486
+ end
487
+ end
488
+
489
+ def test_using_resource_with_parent_for_get
490
+ @request.accept = "application/xml"
491
+ get :using_resource_with_parent
492
+ assert_equal "application/xml", @response.content_type
493
+ assert_equal 200, @response.status
494
+ assert_equal "<name>david</name>", @response.body
495
+ end
496
+
497
+ def test_using_resource_with_parent_for_post
498
+ with_test_route_set do
499
+ @request.accept = "application/xml"
500
+
501
+ post :using_resource_with_parent
502
+ assert_equal "application/xml", @response.content_type
503
+ assert_equal 201, @response.status
504
+ assert_equal "<name>david</name>", @response.body
505
+ assert_equal "http://www.example.com/quiz_stores/11/customers/13", @response.location
506
+
507
+ errors = { :name => :invalid }
508
+ Customer.any_instance.stubs(:errors).returns(errors)
509
+ post :using_resource
510
+ assert_equal "application/xml", @response.content_type
511
+ assert_equal 422, @response.status
512
+ assert_equal errors.to_xml, @response.body
513
+ assert_nil @response.location
514
+ end
515
+ end
516
+
517
+ def test_using_resource_with_collection
518
+ @request.accept = "application/xml"
519
+ get :using_resource_with_collection
520
+ assert_equal "application/xml", @response.content_type
521
+ assert_equal 200, @response.status
522
+ assert_match(/<name>david<\/name>/, @response.body)
523
+ assert_match(/<name>jamis<\/name>/, @response.body)
524
+ end
525
+
526
+ def test_using_resource_with_action
527
+ @controller.instance_eval do
528
+ def render(params={})
529
+ self.response_body = "#{params[:action]} - #{formats}"
530
+ end
531
+ end
532
+
533
+ errors = { :name => :invalid }
534
+ Customer.any_instance.stubs(:errors).returns(errors)
535
+
536
+ post :using_resource_with_action
537
+ assert_equal "foo - #{[:html].to_s}", @controller.response.body
538
+ end
539
+
540
+ def test_respond_as_responder_entry_point
541
+ @request.accept = "text/html"
542
+ get :using_responder_with_respond
543
+ assert_equal "respond html", @response.body
544
+
545
+ @request.accept = "application/xml"
546
+ get :using_responder_with_respond
547
+ assert_equal "respond xml", @response.body
548
+ end
549
+
550
+ def test_clear_respond_to
551
+ @controller = InheritedRespondWithController.new
552
+ @request.accept = "text/html"
553
+ assert_raises(ActionController::UnknownFormat) do
554
+ get :index
555
+ end
556
+ end
557
+
558
+ def test_first_in_respond_to_has_higher_priority
559
+ @controller = InheritedRespondWithController.new
560
+ @request.accept = "*/*"
561
+ get :index
562
+ assert_equal "application/xml", @response.content_type
563
+ assert_equal "<name>david</name>", @response.body
564
+ end
565
+
566
+ def test_block_inside_respond_with_is_rendered
567
+ @controller = InheritedRespondWithController.new
568
+ @request.accept = "application/json"
569
+ get :index
570
+ assert_equal "JSON", @response.body
571
+ end
572
+
573
+ def test_no_double_render_is_raised
574
+ @request.accept = "text/html"
575
+ assert_raise ActionView::MissingTemplate do
576
+ get :using_resource
577
+ end
578
+ end
579
+
580
+ def test_using_resource_with_status_and_location
581
+ @request.accept = "text/html"
582
+ post :using_resource_with_status_and_location
583
+ assert @response.redirect?
584
+ assert_equal "http://test.host/", @response.location
585
+
586
+ @request.accept = "application/xml"
587
+ get :using_resource_with_status_and_location
588
+ assert_equal 201, @response.status
589
+ end
590
+
591
+ def test_using_resource_with_status_and_location_with_invalid_resource
592
+ errors = { :name => :invalid }
593
+ Customer.any_instance.stubs(:errors).returns(errors)
594
+
595
+ @request.accept = "text/xml"
596
+
597
+ post :using_resource_with_status_and_location
598
+ assert_equal errors.to_xml, @response.body
599
+ assert_equal 422, @response.status
600
+ assert_equal nil, @response.location
601
+
602
+ put :using_resource_with_status_and_location
603
+ assert_equal errors.to_xml, @response.body
604
+ assert_equal 422, @response.status
605
+ assert_equal nil, @response.location
606
+ end
607
+
608
+ def test_using_invalid_resource_with_template
609
+ errors = { :name => :invalid }
610
+ Customer.any_instance.stubs(:errors).returns(errors)
611
+
612
+ @request.accept = "text/xml"
613
+
614
+ post :using_invalid_resource_with_template
615
+ assert_equal errors.to_xml, @response.body
616
+ assert_equal 422, @response.status
617
+ assert_equal nil, @response.location
618
+
619
+ put :using_invalid_resource_with_template
620
+ assert_equal errors.to_xml, @response.body
621
+ assert_equal 422, @response.status
622
+ assert_equal nil, @response.location
623
+ end
624
+
625
+ def test_using_options_with_template
626
+ @request.accept = "text/xml"
627
+
628
+ post :using_options_with_template
629
+ assert_equal "<customer-name>david</customer-name>", @response.body
630
+ assert_equal 123, @response.status
631
+ assert_equal "http://test.host/", @response.location
632
+
633
+ put :using_options_with_template
634
+ assert_equal "<customer-name>david</customer-name>", @response.body
635
+ assert_equal 123, @response.status
636
+ assert_equal "http://test.host/", @response.location
637
+ end
638
+
639
+ def test_using_resource_with_responder
640
+ get :using_resource_with_responder
641
+ assert_equal "Resource name is david", @response.body
642
+ end
643
+
644
+ def test_using_resource_with_set_responder
645
+ RespondWithController.responder = proc { |c, r, o| c.render :text => "Resource name is #{r.first.name}" }
646
+ get :using_resource
647
+ assert_equal "Resource name is david", @response.body
648
+ ensure
649
+ RespondWithController.responder = ActionController::Responder
650
+ end
651
+
652
+ def test_raises_missing_renderer_if_an_api_behavior_with_no_renderer
653
+ @controller = CsvRespondWithController.new
654
+ assert_raise ActionController::MissingRenderer do
655
+ get :index, format: 'csv'
656
+ end
657
+ end
658
+
659
+ def test_error_is_raised_if_no_respond_to_is_declared_and_respond_with_is_called
660
+ @controller = EmptyRespondWithController.new
661
+ @request.accept = "*/*"
662
+ assert_raise RuntimeError do
663
+ get :index
664
+ end
665
+ end
666
+
667
+ private
668
+ def with_test_route_set
669
+ with_routing do |set|
670
+ set.draw do
671
+ resources :customers
672
+ resources :quiz_stores do
673
+ resources :customers
674
+ end
675
+ get ":controller/:action"
676
+ end
677
+ yield
678
+ end
679
+ end
680
+ end
681
+
682
+ class LocationsController < ApplicationController
683
+ respond_to :html
684
+ before_filter :set_resource
685
+
686
+ def create
687
+ respond_with @resource, location: -> { 'given_location' }
688
+ end
689
+
690
+ def update
691
+ respond_with @resource, location: 'given_location'
692
+ end
693
+
694
+ def set_resource
695
+ @resource = Address.new
696
+ @resource.errors[:fail] << "FAIL" if params[:fail]
697
+ end
698
+ end
699
+
700
+ class LocationResponderTest < ActionController::TestCase
701
+ tests LocationsController
702
+
703
+ def test_redirects_to_block_location_on_success
704
+ post :create
705
+ assert_redirected_to 'given_location'
706
+ end
707
+
708
+ def test_renders_page_on_fail
709
+ post :create, fail: true
710
+ assert @response.body.include?('new.html.erb')
711
+ end
712
+
713
+ def test_redirects_to_plain_string
714
+ post :update
715
+ assert_redirected_to 'given_location'
716
+ end
717
+ end