josevalim-inherited_resources 0.1
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/CHANGELOG +4 -0
- data/MIT-LICENSE +21 -0
- data/README +362 -0
- data/Rakefile +19 -0
- data/init.rb +1 -0
- data/lib/inherited_resources.rb +4 -0
- data/lib/inherited_resources/base.rb +272 -0
- data/lib/inherited_resources/base_helpers.rb +199 -0
- data/lib/inherited_resources/belongs_to.rb +227 -0
- data/lib/inherited_resources/belongs_to_helpers.rb +89 -0
- data/lib/inherited_resources/class_methods.rb +155 -0
- data/lib/inherited_resources/polymorphic_helpers.rb +19 -0
- data/lib/inherited_resources/respond_to.rb +324 -0
- data/lib/inherited_resources/singleton_helpers.rb +53 -0
- data/lib/inherited_resources/url_helpers.rb +147 -0
- data/test/aliases_test.rb +71 -0
- data/test/base_helpers_test.rb +130 -0
- data/test/base_test.rb +219 -0
- data/test/belongs_to_base_test.rb +268 -0
- data/test/belongs_to_test.rb +109 -0
- data/test/class_methods_test.rb +73 -0
- data/test/fixtures/en.yml +9 -0
- data/test/nested_belongs_to_test.rb +138 -0
- data/test/polymorphic_base_test.rb +282 -0
- data/test/respond_to_test.rb +282 -0
- data/test/singleton_base_test.rb +226 -0
- data/test/test_helper.rb +37 -0
- data/test/url_helpers_test.rb +284 -0
- data/test/views/cities/edit.html.erb +1 -0
- data/test/views/cities/index.html.erb +1 -0
- data/test/views/cities/new.html.erb +1 -0
- data/test/views/cities/show.html.erb +1 -0
- data/test/views/comments/edit.html.erb +1 -0
- data/test/views/comments/index.html.erb +1 -0
- data/test/views/comments/new.html.erb +1 -0
- data/test/views/comments/show.html.erb +1 -0
- data/test/views/employees/edit.html.erb +1 -0
- data/test/views/employees/index.html.erb +1 -0
- data/test/views/employees/new.html.erb +1 -0
- data/test/views/employees/show.html.erb +1 -0
- data/test/views/managers/edit.html.erb +1 -0
- data/test/views/managers/new.html.erb +1 -0
- data/test/views/managers/show.html.erb +1 -0
- data/test/views/pets/edit.html.erb +1 -0
- data/test/views/professors/edit.html.erb +1 -0
- data/test/views/professors/index.html.erb +1 -0
- data/test/views/professors/new.html.erb +1 -0
- data/test/views/professors/show.html.erb +1 -0
- data/test/views/projects/index.html.erb +1 -0
- data/test/views/projects/respond_to_with_resource.html.erb +1 -0
- data/test/views/students/edit.html.erb +1 -0
- data/test/views/students/new.html.erb +1 -0
- data/test/views/users/edit.html.erb +1 -0
- data/test/views/users/index.html.erb +1 -0
- data/test/views/users/new.html.erb +1 -0
- data/test/views/users/show.html.erb +1 -0
- metadata +108 -0
@@ -0,0 +1,155 @@
|
|
1
|
+
# = singleton
|
2
|
+
#
|
3
|
+
# Singletons are usually used in associations which are related through has_one
|
4
|
+
# and belongs_to. You declare those associations like this:
|
5
|
+
#
|
6
|
+
# class ManagersController < InheritedResources::Base
|
7
|
+
# belongs_to :project, :singleton => true
|
8
|
+
# end
|
9
|
+
#
|
10
|
+
# But in some cases, like an AccountsController, you have a singleton object
|
11
|
+
# that is not necessarily associated with another:
|
12
|
+
#
|
13
|
+
# class AccountsController < InheritedResources::Base
|
14
|
+
# defaults :singleton => true
|
15
|
+
# end
|
16
|
+
#
|
17
|
+
# Besides that, you should overwrite the methods :resource and :build_resource
|
18
|
+
# to make it work properly:
|
19
|
+
#
|
20
|
+
# class AccountsController < InheritedResources::Base
|
21
|
+
# defaults :singleton => true
|
22
|
+
#
|
23
|
+
# protected
|
24
|
+
# def resource
|
25
|
+
# @current_user.account
|
26
|
+
# end
|
27
|
+
#
|
28
|
+
# def build_resource(attributes = {})
|
29
|
+
# Account.new(attributes)
|
30
|
+
# end
|
31
|
+
# end
|
32
|
+
#
|
33
|
+
# When you have a singleton controller, the action index is removed.
|
34
|
+
#
|
35
|
+
module InheritedResources #:nodoc:
|
36
|
+
RESOURCES_CLASS_ACCESSORS = [ :resource_class, :resources_configuration, :parents_symbols, :singleton, :polymorphic_symbols ]
|
37
|
+
|
38
|
+
module ClassMethods #:nodoc:
|
39
|
+
|
40
|
+
protected
|
41
|
+
|
42
|
+
# When you inherit from InheritedResources::Base, we make some assumptions on
|
43
|
+
# what is your resource_class, instance_name and collection_name.
|
44
|
+
#
|
45
|
+
# You can change those values by calling the class method defaults:
|
46
|
+
#
|
47
|
+
# class PeopleController < InheritedResources::Base
|
48
|
+
# defaults :resource_class => User, :instance_name => 'user', :collection_name => 'users'
|
49
|
+
# end
|
50
|
+
#
|
51
|
+
# You can also provide :class_name, which is the same as :resource_class
|
52
|
+
# but accepts string (this is given for ActiveRecord compatibility).
|
53
|
+
#
|
54
|
+
def defaults(options)
|
55
|
+
raise ArgumentError, 'Class method :defaults expects a hash of options.' unless options.is_a? Hash
|
56
|
+
|
57
|
+
options.symbolize_keys!
|
58
|
+
options.assert_valid_keys(:resource_class, :collection_name, :instance_name, :class_name, :singleton)
|
59
|
+
|
60
|
+
# Checks for special argument :resource_class and :class_name and sets it right away.
|
61
|
+
self.resource_class = options.delete(:resource_class) if options[:resource_class]
|
62
|
+
self.resource_class = options.delete(:class_name).constantize if options[:class_name]
|
63
|
+
|
64
|
+
acts_as_singleton! if options.delete(:singleton)
|
65
|
+
|
66
|
+
options.each do |key, value|
|
67
|
+
self.resources_configuration[:self][key] = value.to_sym
|
68
|
+
end
|
69
|
+
|
70
|
+
InheritedResources::UrlHelpers.create_resources_url_helpers!(self)
|
71
|
+
end
|
72
|
+
|
73
|
+
# Defines wich actions to keep from the inherited controller.
|
74
|
+
# Syntax is borrowed from resource_controller.
|
75
|
+
#
|
76
|
+
# actions :index, :show, :edit
|
77
|
+
# actions :all, :except => :index
|
78
|
+
#
|
79
|
+
def actions(*actions_to_keep)
|
80
|
+
raise ArgumentError, 'Wrong number of arguments. You have to provide which actions you want to keep.' if actions_to_keep.empty?
|
81
|
+
|
82
|
+
options = actions_to_keep.extract_options!
|
83
|
+
actions_to_keep.map!{ |a| a.to_s }
|
84
|
+
|
85
|
+
actions_to_remove = Array(options[:except])
|
86
|
+
actions_to_remove.map!{ |a| a.to_s }
|
87
|
+
|
88
|
+
actions_to_remove += RESOURCES_ACTIONS.map{|a| a.to_s } - actions_to_keep unless actions_to_keep.first == 'all'
|
89
|
+
actions_to_remove.uniq!
|
90
|
+
|
91
|
+
# Undefine actions that we don't want
|
92
|
+
(instance_methods & actions_to_remove).each do |action|
|
93
|
+
undef_method action, "#{action}!"
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
private
|
98
|
+
|
99
|
+
# Defines this controller as singleton.
|
100
|
+
# You can call this method to define your controller as singleton.
|
101
|
+
#
|
102
|
+
def acts_as_singleton!
|
103
|
+
unless self.singleton
|
104
|
+
self.singleton = true
|
105
|
+
include SingletonHelpers
|
106
|
+
actions :all, :except => :index
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
# Defines this controller as polymorphic.
|
111
|
+
# Do not call this method on your own.
|
112
|
+
#
|
113
|
+
def acts_as_polymorphic!
|
114
|
+
if self.polymorphic_symbols.empty?
|
115
|
+
include PolymorphicHelpers
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
# Initialize resources class accessors by creating the accessors
|
120
|
+
# and setting their default values.
|
121
|
+
#
|
122
|
+
def initialize_resources_class_accessors!(base)
|
123
|
+
# Add and protect class accessors
|
124
|
+
base.class_eval do
|
125
|
+
RESOURCES_CLASS_ACCESSORS.each do |cattr|
|
126
|
+
cattr_accessor "#{cattr}", :instance_writer => false
|
127
|
+
|
128
|
+
# Protect instance methods
|
129
|
+
self.send :protected, cattr
|
130
|
+
|
131
|
+
# Protect class writer
|
132
|
+
metaclass.send :protected, "#{cattr}="
|
133
|
+
end
|
134
|
+
end
|
135
|
+
|
136
|
+
# Initialize resource class
|
137
|
+
base.resource_class = base.controller_name.classify.constantize rescue nil
|
138
|
+
|
139
|
+
# Initialize resources configuration hash
|
140
|
+
base.resources_configuration = {}
|
141
|
+
config = base.resources_configuration[:self] = {}
|
142
|
+
config[:collection_name] = base.controller_name.to_sym
|
143
|
+
config[:instance_name] = base.controller_name.singularize.to_sym
|
144
|
+
|
145
|
+
# Initialize polymorphic, singleton and belongs_to parameters
|
146
|
+
base.singleton = false
|
147
|
+
base.parents_symbols = []
|
148
|
+
base.polymorphic_symbols = []
|
149
|
+
|
150
|
+
# Create helpers
|
151
|
+
InheritedResources::UrlHelpers.create_resources_url_helpers!(base)
|
152
|
+
end
|
153
|
+
|
154
|
+
end
|
155
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module InheritedResources #:nodoc:
|
2
|
+
module PolymorphicHelpers #:nodoc:
|
3
|
+
|
4
|
+
protected
|
5
|
+
|
6
|
+
def parent_type
|
7
|
+
@parent_type
|
8
|
+
end
|
9
|
+
|
10
|
+
def parent_class
|
11
|
+
parent_instance.class
|
12
|
+
end
|
13
|
+
|
14
|
+
def parent_instance
|
15
|
+
instance_variable_get("@#{@parent_type}")
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
@@ -0,0 +1,324 @@
|
|
1
|
+
# Provides an extension for Rails respond_to by expading MimeResponds::Responder
|
2
|
+
# and adding respond_to class method and respond_with instance method.
|
3
|
+
#
|
4
|
+
module ActionController #:nodoc:
|
5
|
+
class Base #:nodoc:
|
6
|
+
|
7
|
+
protected
|
8
|
+
# Defines respond_to method to store formats that are rendered by default.
|
9
|
+
#
|
10
|
+
# Examples:
|
11
|
+
#
|
12
|
+
# respond_to :html, :xml, :json
|
13
|
+
#
|
14
|
+
# All actions on your controller will respond to :html, :xml and :json.
|
15
|
+
# But if you want to specify it based on your actions, you can use only and
|
16
|
+
# except:
|
17
|
+
#
|
18
|
+
# respond_to :html
|
19
|
+
# respond_to :xml, :json, :except => [ :edit ]
|
20
|
+
#
|
21
|
+
# The definition above explicits that all actions respond to :html. And all
|
22
|
+
# actions except :edit respond to :xml and :json.
|
23
|
+
#
|
24
|
+
# You can specify also only parameters:
|
25
|
+
#
|
26
|
+
# respond_to :rjs, :only => :create
|
27
|
+
#
|
28
|
+
# Which would be the same as:
|
29
|
+
#
|
30
|
+
# respond_to :rjs => :create
|
31
|
+
#
|
32
|
+
def self.respond_to(*formats)
|
33
|
+
options = formats.extract_options!
|
34
|
+
formats_hash = {}
|
35
|
+
|
36
|
+
only_actions = Array(options.delete(:only))
|
37
|
+
except_actions = Array(options.delete(:except))
|
38
|
+
|
39
|
+
only_actions.map!{ |a| a.to_sym }
|
40
|
+
except_actions.map!{ |a| a.to_sym }
|
41
|
+
|
42
|
+
formats.each do |format|
|
43
|
+
formats_hash[format.to_sym] = {}
|
44
|
+
formats_hash[format.to_sym][:only] = only_actions unless only_actions.empty?
|
45
|
+
formats_hash[format.to_sym][:except] = except_actions unless except_actions.empty?
|
46
|
+
end
|
47
|
+
|
48
|
+
options.each do |format, actions|
|
49
|
+
formats_hash[format.to_sym] = {}
|
50
|
+
next if actions == :all || actions == 'all'
|
51
|
+
|
52
|
+
actions = Array(actions)
|
53
|
+
actions.map!{ |a| a.to_sym }
|
54
|
+
|
55
|
+
formats_hash[format.to_sym][:only] = actions unless actions.empty?
|
56
|
+
end
|
57
|
+
|
58
|
+
write_inheritable_hash(:formats_for_respond_to, formats_hash)
|
59
|
+
end
|
60
|
+
class_inheritable_reader :formats_for_respond_to
|
61
|
+
|
62
|
+
# Define defaults respond_to
|
63
|
+
respond_to :html
|
64
|
+
respond_to :xml, :except => [ :edit ]
|
65
|
+
|
66
|
+
# Method to clear all respond_to declared until the current controller.
|
67
|
+
# This is like freeing the controller from the inheritance chain. :)
|
68
|
+
#
|
69
|
+
def self.clear_respond_to!
|
70
|
+
formats = formats_for_respond_to
|
71
|
+
formats.each { |k,v| formats[k] = { :only => [] } }
|
72
|
+
write_inheritable_hash(:formats_for_respond_to, formats)
|
73
|
+
end
|
74
|
+
|
75
|
+
# respond_with accepts an object and tries to render a view based in the
|
76
|
+
# controller and actions that called respond_with. If the view cannot be
|
77
|
+
# found, it will try to call :to_format in the object.
|
78
|
+
#
|
79
|
+
# class ProjectsController < ApplicationController
|
80
|
+
# respond_to :html, :xml
|
81
|
+
#
|
82
|
+
# def show
|
83
|
+
# @project = Project.find(:id)
|
84
|
+
# respond_with(@project)
|
85
|
+
# end
|
86
|
+
# end
|
87
|
+
#
|
88
|
+
# When the client request a xml, we will check first for projects/show.xml
|
89
|
+
# if it can't be found, we will call :to_xml in the object @project. If the
|
90
|
+
# object eventually doesn't respond to :to_xml it will render 404.
|
91
|
+
#
|
92
|
+
# If you want to overwrite the formats specified in the class, you can
|
93
|
+
# send your new formats using the options :to.
|
94
|
+
#
|
95
|
+
# def show
|
96
|
+
# @project = Project.find(:id)
|
97
|
+
# respond_with(@project, :to => :json)
|
98
|
+
# end
|
99
|
+
#
|
100
|
+
# That means that this action will ONLY reply to json requests.
|
101
|
+
#
|
102
|
+
# All other options sent will be forwarded to the render method. So you can
|
103
|
+
# do:
|
104
|
+
#
|
105
|
+
# def create
|
106
|
+
# # ...
|
107
|
+
# if @project.save
|
108
|
+
# respond_with(@project, :status => :ok, :location => @project)
|
109
|
+
# else
|
110
|
+
# respond_with(@project.errors, :status => :unprocessable_entity)
|
111
|
+
# end
|
112
|
+
# end
|
113
|
+
#
|
114
|
+
# respond_with does not accept blocks, if you want advanced configurations
|
115
|
+
# check respond_to method sending :with => @object as option.
|
116
|
+
#
|
117
|
+
# Returns true if anything is rendered. Returns false otherwise.
|
118
|
+
#
|
119
|
+
def respond_with(object, options = {})
|
120
|
+
attempt_to_respond = false
|
121
|
+
|
122
|
+
# You can also send a responder object as parameter.
|
123
|
+
#
|
124
|
+
responder = options.delete(:responder) || Responder.new(self)
|
125
|
+
|
126
|
+
# Check for given mime types
|
127
|
+
#
|
128
|
+
mime_types = Array(options.delete(:to))
|
129
|
+
mime_types.map!{ |mime| mime.to_sym }
|
130
|
+
|
131
|
+
# If :skip_not_acceptable is sent, it will not render :not_acceptable
|
132
|
+
# if the mime type sent by the client cannot be found.
|
133
|
+
#
|
134
|
+
skip_not_acceptable = options.delete(:skip_not_acceptable)
|
135
|
+
|
136
|
+
for priority in responder.mime_type_priority
|
137
|
+
if priority == Mime::ALL && template_exists?
|
138
|
+
render options.merge(:action => action_name)
|
139
|
+
return true
|
140
|
+
|
141
|
+
elsif responder.action_respond_to_format?(priority.to_sym, mime_types)
|
142
|
+
attempt_to_respond = true
|
143
|
+
response.template.template_format = priority.to_sym
|
144
|
+
response.content_type = priority.to_s
|
145
|
+
|
146
|
+
if template_exists?
|
147
|
+
render options.merge(:action => action_name)
|
148
|
+
return true
|
149
|
+
elsif object.respond_to?(:"to_#{priority.to_sym}")
|
150
|
+
render options.merge(:text => object.send(:"to_#{priority.to_sym}"))
|
151
|
+
return true
|
152
|
+
end
|
153
|
+
end
|
154
|
+
end
|
155
|
+
|
156
|
+
# If we got here we could not render the object. But if attempted to
|
157
|
+
# render (this means, the format sent by the client was valid) we should
|
158
|
+
# render a 404.
|
159
|
+
#
|
160
|
+
# If we even didn't attempt to respond, we respond :not_acceptable
|
161
|
+
# unless is told otherwise.
|
162
|
+
#
|
163
|
+
if attempt_to_respond
|
164
|
+
render :text => '404 Not Found', :status => 404
|
165
|
+
return true
|
166
|
+
elsif !skip_not_acceptable
|
167
|
+
head :not_acceptable
|
168
|
+
return false
|
169
|
+
end
|
170
|
+
|
171
|
+
return false
|
172
|
+
end
|
173
|
+
|
174
|
+
# Extends respond_to behaviour.
|
175
|
+
#
|
176
|
+
# You can now pass objects using the options :with.
|
177
|
+
#
|
178
|
+
# respond_to(:html, :xml, :rjs, :with => @project)
|
179
|
+
#
|
180
|
+
# If you pass an object and send any block, it's exactly the same as:
|
181
|
+
#
|
182
|
+
# respond_with(@project, :to => [:html, :xml, :rjs])
|
183
|
+
#
|
184
|
+
# But the main difference of respond_to and respond_with is that the first
|
185
|
+
# allows further customizations:
|
186
|
+
#
|
187
|
+
# respond_to(:html, :with => @project) do |format|
|
188
|
+
# format.xml { render :xml => @project.errors }
|
189
|
+
# end
|
190
|
+
#
|
191
|
+
# It's the same as:
|
192
|
+
#
|
193
|
+
# 1. When responding to html, execute respond_with(@object).
|
194
|
+
# 2. When accessing a xml, execute the block given.
|
195
|
+
#
|
196
|
+
# Formats defined in blocks have precedence to formats sent as arguments.
|
197
|
+
# In other words, if you pass a format as argument and as block, the block
|
198
|
+
# will always be executed.
|
199
|
+
#
|
200
|
+
# And as in respond_with, all extra options sent will be forwarded to
|
201
|
+
# the render method:
|
202
|
+
#
|
203
|
+
# respond_to(:with => @projects.errors, :status => :unprocessable_entity) do |format|
|
204
|
+
# format.html { render :template => 'new' }
|
205
|
+
# end
|
206
|
+
#
|
207
|
+
def respond_to(*types, &block)
|
208
|
+
options = types.extract_options!
|
209
|
+
object = options.delete(:with)
|
210
|
+
responder = Responder.new(self)
|
211
|
+
|
212
|
+
# This is the default respond_to behaviour, when no object is given.
|
213
|
+
if object.nil?
|
214
|
+
block ||= lambda { |responder| types.each { |type| responder.send(type) } }
|
215
|
+
block.call(responder)
|
216
|
+
responder.respond
|
217
|
+
return true # we are done here
|
218
|
+
|
219
|
+
else
|
220
|
+
# If a block is given, it checks if we can perform the requested format.
|
221
|
+
#
|
222
|
+
# Even if Mime::ALL is sent by the client, we do not respond_to it now.
|
223
|
+
# This is done using calling :respond_to_block instead of :respond.
|
224
|
+
#
|
225
|
+
# It's worth to remember that responder_to_block does not respond
|
226
|
+
# :not_acceptable also.
|
227
|
+
#
|
228
|
+
if block_given?
|
229
|
+
block.call(responder)
|
230
|
+
responder.respond_to_block
|
231
|
+
return true if responder.responded? || performed?
|
232
|
+
end
|
233
|
+
|
234
|
+
# Let's see if we get lucky rendering with :respond_with.
|
235
|
+
# At the end, respond_with checks for Mime::ALL if any template exist.
|
236
|
+
#
|
237
|
+
# Notice that we are sending the responder (for performance gain) and
|
238
|
+
# sending :skip_not_acceptable because we don't want to respond
|
239
|
+
# :not_acceptable yet.
|
240
|
+
#
|
241
|
+
if respond_with(object, options.merge(:to => types, :responder => responder, :skip_not_acceptable => true))
|
242
|
+
return true
|
243
|
+
|
244
|
+
# Since respond_with couldn't help us, our last chance is to reply to
|
245
|
+
# any block given if the user send all as mime type.
|
246
|
+
#
|
247
|
+
elsif block_given?
|
248
|
+
return true if responder.respond_to_all
|
249
|
+
end
|
250
|
+
end
|
251
|
+
|
252
|
+
# If we get here it means that we could not satisfy our request.
|
253
|
+
# Now we finally return :not_acceptable.
|
254
|
+
#
|
255
|
+
head :not_acceptable
|
256
|
+
return false
|
257
|
+
end
|
258
|
+
end
|
259
|
+
|
260
|
+
module MimeResponds #:nodoc:
|
261
|
+
class Responder #:nodoc:
|
262
|
+
|
263
|
+
# Create an attr_reader for @mime_type_priority
|
264
|
+
attr_reader :mime_type_priority
|
265
|
+
|
266
|
+
# Stores if this Responder instance called any block.
|
267
|
+
def responded?; @responded; end
|
268
|
+
|
269
|
+
# Similar as respond but if we can't find a valid mime type,
|
270
|
+
# we do not send :not_acceptable message as head.
|
271
|
+
#
|
272
|
+
# It does not respond to Mime::ALL in priority as well.
|
273
|
+
#
|
274
|
+
def respond_to_block
|
275
|
+
for priority in @mime_type_priority
|
276
|
+
next if priority == Mime::ALL
|
277
|
+
|
278
|
+
if @responses[priority]
|
279
|
+
@responses[priority].call
|
280
|
+
return (@responded = true) # mime type match found, be happy and return
|
281
|
+
end
|
282
|
+
end
|
283
|
+
|
284
|
+
if @order.include?(Mime::ALL)
|
285
|
+
@responses[Mime::ALL].call
|
286
|
+
return (@responded = true)
|
287
|
+
else
|
288
|
+
return (@responded = false)
|
289
|
+
end
|
290
|
+
end
|
291
|
+
|
292
|
+
# Respond to the first format given if Mime::ALL is included in the
|
293
|
+
# mime type priorites. This is the behaviour expected when the client
|
294
|
+
# sends "*/*" as mime type.
|
295
|
+
#
|
296
|
+
def respond_to_all
|
297
|
+
if @mime_type_priority.include?(Mime::ALL) && first = @responses[@order.first]
|
298
|
+
first.call
|
299
|
+
return (@responded = true)
|
300
|
+
end
|
301
|
+
end
|
302
|
+
|
303
|
+
# Receives an format and checks if the current action responds to
|
304
|
+
# the given format. If additional mimes are sent, only them are checked.
|
305
|
+
#
|
306
|
+
def action_respond_to_format?(format, additional_mimes = [])
|
307
|
+
if !additional_mimes.blank?
|
308
|
+
additional_mimes.include?(format.to_sym)
|
309
|
+
elsif formats = @controller.formats_for_respond_to[format.to_sym]
|
310
|
+
if formats[:only]
|
311
|
+
formats[:only].include?(@controller.action_name.to_sym)
|
312
|
+
elsif formats[:except]
|
313
|
+
!formats[:except].include?(@controller.action_name.to_sym)
|
314
|
+
else
|
315
|
+
true
|
316
|
+
end
|
317
|
+
else
|
318
|
+
false
|
319
|
+
end
|
320
|
+
end
|
321
|
+
|
322
|
+
end
|
323
|
+
end
|
324
|
+
end
|