diff options
Diffstat (limited to 'actionpack/lib')
-rwxr-xr-x | actionpack/lib/action_controller.rb | 2 | ||||
-rwxr-xr-x | actionpack/lib/action_controller/base.rb | 13 | ||||
-rw-r--r-- | actionpack/lib/action_controller/mime_responds.rb | 53 | ||||
-rw-r--r-- | actionpack/lib/action_controller/mime_type.rb | 44 | ||||
-rwxr-xr-x | actionpack/lib/action_controller/request.rb | 19 | ||||
-rw-r--r-- | actionpack/lib/action_controller/test_process.rb | 2 | ||||
-rw-r--r-- | actionpack/lib/action_view/helpers/javascripts/prototype.js | 3 |
7 files changed, 126 insertions, 10 deletions
diff --git a/actionpack/lib/action_controller.rb b/actionpack/lib/action_controller.rb index b51e5b45bc..593a283824 100755 --- a/actionpack/lib/action_controller.rb +++ b/actionpack/lib/action_controller.rb @@ -44,6 +44,7 @@ require 'action_controller/flash' require 'action_controller/filters' require 'action_controller/layout' require 'action_controller/dependencies' +require 'action_controller/mime_responds' require 'action_controller/pagination' require 'action_controller/scaffolding' require 'action_controller/helpers' @@ -67,6 +68,7 @@ ActionController::Base.class_eval do include ActionController::Benchmarking include ActionController::Rescue include ActionController::Dependencies + include ActionController::MimeResponds include ActionController::Pagination include ActionController::Scaffolding include ActionController::Helpers diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 05c8796f81..c6c052ec56 100755 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -1,3 +1,4 @@ +require 'action_controller/mime_type' require 'action_controller/request' require 'action_controller/response' require 'action_controller/routing' @@ -648,7 +649,10 @@ module ActionController #:nodoc: elsif action_name = options[:action] render_action(action_name, options[:status], options[:layout]) - + + elsif xml = options[:xml] + render_xml(xml, options[:status]) + elsif partial = options[:partial] partial = default_template_name if partial == true if collection = options[:collection] @@ -715,10 +719,15 @@ module ActionController #:nodoc: end def render_javascript(javascript, status = nil) - @response.headers['Content-Type'] = 'text/javascript' + @response.headers['Content-Type'] = 'text/javascript; charset=UTF-8' render_text(javascript, status) end + def render_xml(xml, status = nil) + @response.headers['Content-Type'] = 'text/xml; charset=UTF-8' + render_text(xml, status) + end + def render_nothing(status = nil) render_text(' ', status) end diff --git a/actionpack/lib/action_controller/mime_responds.rb b/actionpack/lib/action_controller/mime_responds.rb new file mode 100644 index 0000000000..7a60a5cc37 --- /dev/null +++ b/actionpack/lib/action_controller/mime_responds.rb @@ -0,0 +1,53 @@ +module ActionController #:nodoc: + module MimeResponds #:nodoc: + def self.included(base) + base.send(:include, ActionController::MimeResponds::InstanceMethods) + end + + module InstanceMethods + def respond_to(&block) + responder = Responder.new(block.binding) + yield responder + responder.respond + end + end + + class Responder #:nodoc: + def initialize(block_binding) + @block_binding = block_binding + @mime_type_priority = eval("request.accepts", block_binding) + @order = [] + @responses = {} + end + + for mime_type in %w( all html js xml rss atom yaml ) + eval <<-EOT + def #{mime_type}(&block) + @order << Mime::#{mime_type.upcase} + @responses[Mime::#{mime_type.upcase}] = block + end + EOT + end + + def respond + for priority in @mime_type_priority + if priority == Mime::ALL + @responses[@order.first].call + return + else + if @order.include?(priority) + @responses[priority].call + return # mime type match found, be happy and return + end + end + end + + if @order.include?(Mime::ALL) + @responses[Mime::ALL].call + else + eval 'render(:nothing => true, :status => "406 Not Acceptable")', @block_binding + end + end + end + end +end diff --git a/actionpack/lib/action_controller/mime_type.rb b/actionpack/lib/action_controller/mime_type.rb new file mode 100644 index 0000000000..0ab0221007 --- /dev/null +++ b/actionpack/lib/action_controller/mime_type.rb @@ -0,0 +1,44 @@ +module Mime + class Type < String + def initialize(string, part_of_all = true) + @part_of_all = part_of_all + super(string) + end + + def to_sym + SYMBOLIZED_MIME_TYPES[self] ? SYMBOLIZED_MIME_TYPES[self] : to_sym + end + + def ===(list) + if list.is_a?(Array) + list.include?(self) + else + super + end + end + end + + SYMBOLIZED_MIME_TYPES = { + "" => :unspecified, + "*/*" => :all, + "text/html" => :html, + "application/javascript" => :js, + "application/x-javascript" => :js, + "text/javascript" => :js, + "text/xml" => :xml, + "application/xml" => :xml, + "application/rss+xml" => :rss, + "application/rss+atom" => :atom, + "application/x-xml" => :xml, + "application/x-yaml" => :yaml + } + + ALL = Type.new "*/*" + HTML = Type.new "text/html" + JS = Type.new "text/javascript" + JAVASCRIPT = Type.new "text/javascript" + XML = Type.new "application/xml" + RSS = Type.new "application/rss+xml" + ATOM = Type.new "application/rss+atom" + YAML = Type.new "application/x-yaml" +end
\ No newline at end of file diff --git a/actionpack/lib/action_controller/request.rb b/actionpack/lib/action_controller/request.rb index b55f63e618..16acc50011 100755 --- a/actionpack/lib/action_controller/request.rb +++ b/actionpack/lib/action_controller/request.rb @@ -54,13 +54,20 @@ module ActionController if @env['HTTP_X_POST_DATA_FORMAT'] case @env['HTTP_X_POST_DATA_FORMAT'].downcase.to_sym - when :yaml - @content_type = 'application/x-yaml' - when :xml - @content_type = 'application/xml' - end + when :yaml + @content_type = 'application/x-yaml' + when :xml + @content_type = 'application/xml' + end + end + + @content_type = Mime::Type.new(@content_type) + end + + def accepts + @accepts ||= (@env['HTTP_ACCEPT'].strip.blank? ? "*/*" : @env['HTTP_ACCEPT']).split(";").collect! do |mime_type| + Mime::Type.new(mime_type.strip) end - @content_type end # Returns true if the request's "X-Requested-With" header contains diff --git a/actionpack/lib/action_controller/test_process.rb b/actionpack/lib/action_controller/test_process.rb index 07ef94aad2..afc33afc58 100644 --- a/actionpack/lib/action_controller/test_process.rb +++ b/actionpack/lib/action_controller/test_process.rb @@ -104,7 +104,7 @@ module ActionController #:nodoc: self.request_parameters = {} self.query_parameters = {} self.path_parameters = {} - @request_method = nil + @request_method, @accepts, @content_type = nil, nil, nil end private diff --git a/actionpack/lib/action_view/helpers/javascripts/prototype.js b/actionpack/lib/action_view/helpers/javascripts/prototype.js index c528a4956d..5093f40189 100644 --- a/actionpack/lib/action_view/helpers/javascripts/prototype.js +++ b/actionpack/lib/action_view/helpers/javascripts/prototype.js @@ -703,7 +703,8 @@ Ajax.Request.prototype = Object.extend(new Ajax.Base(), { setRequestHeaders: function() { var requestHeaders = ['X-Requested-With', 'XMLHttpRequest', - 'X-Prototype-Version', Prototype.Version]; + 'X-Prototype-Version', Prototype.Version, + 'Accept', 'text/javascript; text/html; text/xml; */*' ]; if (this.options.method == 'post') { requestHeaders.push('Content-type', |