From b35562f432d0807517a614a540026c2fc557e2ac Mon Sep 17 00:00:00 2001 From: Matt Jones Date: Tue, 24 Feb 2009 10:38:07 -0600 Subject: correctly handle layouts for AJAX requests and regular js files [#2052 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_controller/layout.rb | 21 ++++++++++++++------- actionpack/lib/action_view/paths.rb | 6 +++--- 2 files changed, 17 insertions(+), 10 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/layout.rb b/actionpack/lib/action_controller/layout.rb index a0db7acf72..ccd9605562 100644 --- a/actionpack/lib/action_controller/layout.rb +++ b/actionpack/lib/action_controller/layout.rb @@ -207,21 +207,23 @@ module ActionController #:nodoc: when Proc then layout.call(self) else layout end - - find_layout(active_layout, @template.template_format) if active_layout + + find_layout(active_layout, default_template_format) if active_layout end private def default_layout #:nodoc: - layout = self.class.read_inheritable_attribute(:layout) unless default_template_format == :js + layout = self.class.read_inheritable_attribute(:layout) return layout unless self.class.read_inheritable_attribute(:auto_layout) find_layout(layout, default_template_format) rescue ActionView::MissingTemplate nil end - def find_layout(layout, *formats) #:nodoc: - view_paths.find_template(layout.to_s =~ /layouts\// ? layout : "layouts/#{layout}", *formats) + def find_layout(layout, format) #:nodoc: + view_paths.find_template(layout.to_s =~ /layouts\// ? layout : "layouts/#{layout}", format, false) + rescue ActionView::MissingTemplate + raise if Mime::Type.lookup_by_extension(format.to_s).html? end def pick_layout(options) @@ -258,7 +260,12 @@ module ActionController #:nodoc: template = options[:template] || default_template(options[:action]) if options.values_at(:text, :xml, :json, :file, :inline, :partial, :nothing, :update).compact.empty? begin - !self.view_paths.find_template(template, default_template_format).exempt_from_layout? + template_object = self.view_paths.find_template(template, default_template_format) + # this restores the behavior from 2.2.2, where response.template.template_format was reset + # to :html for :js requests with a matching html template. + # see v2.2.2, ActionView::Base, lines 328-330 + @real_format = :html if response.template.template_format == :js && template_object.format == "html" + !template_object.exempt_from_layout? rescue ActionView::MissingTemplate true end @@ -268,7 +275,7 @@ module ActionController #:nodoc: end def default_template_format - response.template.template_format + @real_format || response.template.template_format end end end diff --git a/actionpack/lib/action_view/paths.rb b/actionpack/lib/action_view/paths.rb index 41f9f486e5..37d96b2f82 100644 --- a/actionpack/lib/action_view/paths.rb +++ b/actionpack/lib/action_view/paths.rb @@ -40,7 +40,7 @@ module ActionView #:nodoc: each(&:load!) end - def find_template(original_template_path, format = nil) + def find_template(original_template_path, format = nil, html_fallback = true) return original_template_path if original_template_path.respond_to?(:render) template_path = original_template_path.sub(/^\//, '') @@ -54,9 +54,9 @@ module ActionView #:nodoc: elsif template = load_path[template_path] return template # Try to find html version if the format is javascript - elsif format == :js && template = load_path["#{template_path}.#{I18n.locale}.html"] + elsif format == :js && html_fallback && template = load_path["#{template_path}.#{I18n.locale}.html"] return template - elsif format == :js && template = load_path["#{template_path}.html"] + elsif format == :js && html_fallback && template = load_path["#{template_path}.html"] return template end end -- cgit v1.2.3 From 85df4841ddb3db3970fa9e798de698cf6f16752a Mon Sep 17 00:00:00 2001 From: thedarkone Date: Tue, 24 Feb 2009 10:41:45 -0600 Subject: Template without a known template handler should only be reachable through its exact path. [#2027 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_view/template.rb | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/template.rb b/actionpack/lib/action_view/template.rb index ea838b9b02..0dd3a7e619 100644 --- a/actionpack/lib/action_view/template.rb +++ b/actionpack/lib/action_view/template.rb @@ -103,12 +103,12 @@ module ActionView #:nodoc: @@exempt_from_layout.merge(regexps) end - attr_accessor :filename, :load_path, :base_path + attr_accessor :template_path, :filename, :load_path, :base_path attr_accessor :locale, :name, :format, :extension delegate :to_s, :to => :path def initialize(template_path, load_path) - template_path = template_path.dup + @template_path = template_path.dup @load_path, @filename = load_path, File.join(load_path, template_path) @base_path, @name, @locale, @format, @extension = split(template_path) @base_path.to_s.gsub!(/\/$/, '') # Push to split method @@ -119,13 +119,20 @@ module ActionView #:nodoc: def accessible_paths paths = [] - paths << path - paths << path_without_extension - if multipart? - formats = format.split(".") - paths << "#{path_without_format_and_extension}.#{formats.first}" - paths << "#{path_without_format_and_extension}.#{formats.second}" + + if valid_extension?(extension) + paths << path + paths << path_without_extension + if multipart? + formats = format.split(".") + paths << "#{path_without_format_and_extension}.#{formats.first}" + paths << "#{path_without_format_and_extension}.#{formats.second}" + end + else + # template without explicit template handler should only be reachable through its exact path + paths << template_path end + paths end -- cgit v1.2.3 From 1b22071b276a2a2b3e65e6db40c6a0aa92d9ebc3 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Tue, 24 Feb 2009 11:34:32 -0600 Subject: Ensure ActiveRecord session store's connections are checked in after each request [#1927 state:resolved] --- actionpack/lib/action_controller/dispatcher.rb | 7 ------- 1 file changed, 7 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/dispatcher.rb b/actionpack/lib/action_controller/dispatcher.rb index ec40b5c4e6..07931e4a4a 100644 --- a/actionpack/lib/action_controller/dispatcher.rb +++ b/actionpack/lib/action_controller/dispatcher.rb @@ -13,7 +13,6 @@ module ActionController end if defined?(ActiveRecord) - after_dispatch :checkin_connections to_prepare(:activerecord_instantiate_observers) { ActiveRecord::Base.instantiate_observers } end @@ -115,11 +114,5 @@ module ActionController def flush_logger Base.logger.flush end - - def checkin_connections - # Don't return connection (and peform implicit rollback) if this request is a part of integration test - return if @env.key?("rack.test") - ActiveRecord::Base.clear_active_connections! - end end end -- cgit v1.2.3 From 0a8c003b1e0459b5bcfa47f49cc74f7a6b3851f8 Mon Sep 17 00:00:00 2001 From: Sam Granieri Date: Sun, 22 Feb 2009 21:24:53 -0600 Subject: Ruby 1.9 compat: silence a warning about regexp languages [#2050 state:committed] Signed-off-by: Jeremy Kemper --- actionpack/lib/action_controller/routing/segments.rb | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing/segments.rb b/actionpack/lib/action_controller/routing/segments.rb index 129e87c139..cbb1a9c09a 100644 --- a/actionpack/lib/action_controller/routing/segments.rb +++ b/actionpack/lib/action_controller/routing/segments.rb @@ -3,7 +3,11 @@ module ActionController class Segment #:nodoc: RESERVED_PCHAR = ':@&=+$,;' SAFE_PCHAR = "#{URI::REGEXP::PATTERN::UNRESERVED}#{RESERVED_PCHAR}" - UNSAFE_PCHAR = Regexp.new("[^#{SAFE_PCHAR}]", false, 'N').freeze + if RUBY_VERSION >= '1.9' + UNSAFE_PCHAR = Regexp.new("[^#{SAFE_PCHAR}]", false).freeze + else + UNSAFE_PCHAR = Regexp.new("[^#{SAFE_PCHAR}]", false, 'N').freeze + end # TODO: Convert :is_optional accessor to read only attr_accessor :is_optional -- cgit v1.2.3 From 3d1d422b8be027417cb640416d154171e75f03d1 Mon Sep 17 00:00:00 2001 From: Eloy Duran Date: Thu, 26 Feb 2009 12:26:17 +0100 Subject: Pass a custom form builder on to nested fields_for calls. [#2023 status:committed] Signed-off-by: David Heinemeier Hansson --- actionpack/lib/action_view/helpers/form_helper.rb | 132 ++++++++++++++-------- 1 file changed, 83 insertions(+), 49 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/form_helper.rb b/actionpack/lib/action_view/helpers/form_helper.rb index 4fef2b443e..a589bcba2a 100644 --- a/actionpack/lib/action_view/helpers/form_helper.rb +++ b/actionpack/lib/action_view/helpers/form_helper.rb @@ -5,17 +5,24 @@ require 'action_view/helpers/form_tag_helper' module ActionView module Helpers - # Form helpers are designed to make working with models much easier compared to using just standard HTML - # elements by providing a set of methods for creating forms based on your models. This helper generates the HTML - # for forms, providing a method for each sort of input (e.g., text, password, select, and so on). When the form - # is submitted (i.e., when the user hits the submit button or form.submit is called via JavaScript), the form inputs will be bundled into the params object and passed back to the controller. + # Form helpers are designed to make working with models much easier + # compared to using just standard HTML elements by providing a set of + # methods for creating forms based on your models. This helper generates + # the HTML for forms, providing a method for each sort of input + # (e.g., text, password, select, and so on). When the form is submitted + # (i.e., when the user hits the submit button or form.submit is + # called via JavaScript), the form inputs will be bundled into the + # params object and passed back to the controller. # - # There are two types of form helpers: those that specifically work with model attributes and those that don't. - # This helper deals with those that work with model attributes; to see an example of form helpers that don't work - # with model attributes, check the ActionView::Helpers::FormTagHelper documentation. + # There are two types of form helpers: those that specifically work with + # model attributes and those that don't. This helper deals with those that + # work with model attributes; to see an example of form helpers that don't + # work with model attributes, check the ActionView::Helpers::FormTagHelper + # documentation. # - # The core method of this helper, form_for, gives you the ability to create a form for a model instance; - # for example, let's say that you have a model Person and want to create a new instance of it: + # The core method of this helper, form_for, gives you the ability to create + # a form for a model instance; for example, let's say that you have a model + # Person and want to create a new instance of it: # # # Note: a @person variable will have been created in the controller. # # For example: @person = Person.new @@ -40,17 +47,22 @@ module ActionView # <%= submit_tag 'Create' %> # <% end %> # - # This example will render the people/_form partial, setting a local variable called form which references the yielded FormBuilder. - # - # The params object created when this form is submitted would look like: + # This example will render the people/_form partial, setting a + # local variable called form which references the yielded + # FormBuilder. The params object created when this form is + # submitted would look like: # # {"action"=>"create", "controller"=>"persons", "person"=>{"first_name"=>"William", "last_name"=>"Smith"}} # - # The params hash has a nested person value, which can therefore be accessed with params[:person] in the controller. - # If were editing/updating an instance (e.g., Person.find(1) rather than Person.new in the controller), the objects - # attribute values are filled into the form (e.g., the person_first_name field would have that person's first name in it). + # The params hash has a nested person value, which can therefore + # be accessed with params[:person] in the controller. If were + # editing/updating an instance (e.g., Person.find(1) rather than + # Person.new in the controller), the objects attribute values are + # filled into the form (e.g., the person_first_name field would + # have that person's first name in it). # - # If the object name contains square brackets the id for the object will be inserted. For example: + # If the object name contains square brackets the id for the object will be + # inserted. For example: # # <%= text_field "person[]", "name" %> # @@ -58,8 +70,10 @@ module ActionView # # # - # If the helper is being used to generate a repetitive sequence of similar form elements, for example in a partial - # used by render_collection_of_partials, the index option may come in handy. Example: + # If the helper is being used to generate a repetitive sequence of similar + # form elements, for example in a partial used by + # render_collection_of_partials, the index option may + # come in handy. Example: # # <%= text_field "person", "name", "index" => 1 %> # @@ -67,14 +81,17 @@ module ActionView # # # - # An index option may also be passed to form_for and fields_for. This automatically applies - # the index to all the nested fields. + # An index option may also be passed to form_for and + # fields_for. This automatically applies the index to + # all the nested fields. # - # There are also methods for helping to build form tags in link:classes/ActionView/Helpers/FormOptionsHelper.html, - # link:classes/ActionView/Helpers/DateHelper.html, and link:classes/ActionView/Helpers/ActiveRecordHelper.html + # There are also methods for helping to build form tags in + # link:classes/ActionView/Helpers/FormOptionsHelper.html, + # link:classes/ActionView/Helpers/DateHelper.html, and + # link:classes/ActionView/Helpers/ActiveRecordHelper.html module FormHelper - # Creates a form and a scope around a specific model object that is used as - # a base for questioning about values for the fields. + # Creates a form and a scope around a specific model object that is used + # as a base for questioning about values for the fields. # # Rails provides succinct resource-oriented form generation with +form_for+ # like this: @@ -86,13 +103,15 @@ module ActionView # <%= f.text_field :author %>
# <% end %> # - # There, +form_for+ is able to generate the rest of RESTful form parameters - # based on introspection on the record, but to understand what it does we - # need to dig first into the alternative generic usage it is based upon. + # There, +form_for+ is able to generate the rest of RESTful form + # parameters based on introspection on the record, but to understand what + # it does we need to dig first into the alternative generic usage it is + # based upon. # # === Generic form_for # - # The generic way to call +form_for+ yields a form builder around a model: + # The generic way to call +form_for+ yields a form builder around a + # model: # # <% form_for :person, :url => { :action => "update" } do |f| %> # <%= f.error_messages %> @@ -103,8 +122,8 @@ module ActionView # <% end %> # # There, the first argument is a symbol or string with the name of the - # object the form is about, and also the name of the instance variable the - # object is stored in. + # object the form is about, and also the name of the instance variable + # the object is stored in. # # The form builder acts as a regular form helper that somehow carries the # model. Thus, the idea is that @@ -137,17 +156,18 @@ module ActionView # In any of its variants, the rightmost argument to +form_for+ is an # optional hash of options: # - # * :url - The URL the form is submitted to. It takes the same fields - # you pass to +url_for+ or +link_to+. In particular you may pass here a - # named route directly as well. Defaults to the current action. + # * :url - The URL the form is submitted to. It takes the same + # fields you pass to +url_for+ or +link_to+. In particular you may pass + # here a named route directly as well. Defaults to the current action. # * :html - Optional HTML attributes for the form tag. # - # Worth noting is that the +form_for+ tag is called in a ERb evaluation block, - # not an ERb output block. So that's <% %>, not <%= %>. + # Worth noting is that the +form_for+ tag is called in a ERb evaluation + # block, not an ERb output block. So that's <% %>, not + # <%= %>. # # Also note that +form_for+ doesn't create an exclusive scope. It's still - # possible to use both the stand-alone FormHelper methods and methods from - # FormTagHelper. For example: + # possible to use both the stand-alone FormHelper methods and methods + # from FormTagHelper. For example: # # <% form_for :person, @person, :url => { :action => "update" } do |f| %> # First name: <%= f.text_field :first_name %> @@ -156,16 +176,16 @@ module ActionView # Admin? : <%= check_box_tag "person[admin]", @person.company.admin? %> # <% end %> # - # This also works for the methods in FormOptionHelper and DateHelper that are - # designed to work with an object as base, like FormOptionHelper#collection_select - # and DateHelper#datetime_select. + # This also works for the methods in FormOptionHelper and DateHelper that + # are designed to work with an object as base, like + # FormOptionHelper#collection_select and DateHelper#datetime_select. # # === Resource-oriented style # - # As we said above, in addition to manually configuring the +form_for+ call, - # you can rely on automated resource identification, which will use the conventions - # and named routes of that approach. This is the preferred way to use +form_for+ - # nowadays. + # As we said above, in addition to manually configuring the +form_for+ + # call, you can rely on automated resource identification, which will use + # the conventions and named routes of that approach. This is the + # preferred way to use +form_for+ nowadays. # # For example, if @post is an existing record you want to edit # @@ -205,8 +225,10 @@ module ActionView # # === Customized form builders # - # You can also build forms using a customized FormBuilder class. Subclass FormBuilder and override or define some more helpers, - # then use your custom builder. For example, let's say you made a helper to automatically add labels to form inputs. + # You can also build forms using a customized FormBuilder class. Subclass + # FormBuilder and override or define some more helpers, then use your + # custom builder. For example, let's say you made a helper to + # automatically add labels to form inputs. # # <% form_for :person, @person, :url => { :action => "update" }, :builder => LabellingFormBuilder do |f| %> # <%= f.text_field :first_name %> @@ -219,16 +241,23 @@ module ActionView # # <%= render :partial => f %> # - # The rendered template is people/_labelling_form and the local variable referencing the form builder is called labelling_form. + # The rendered template is people/_labelling_form and the local + # variable referencing the form builder is called + # labelling_form. + # + # The custom FormBuilder class is automatically merged with the options + # of a nested fields_for call, unless it's explicitely set. # - # In many cases you will want to wrap the above in another helper, so you could do something like the following: + # In many cases you will want to wrap the above in another helper, so you + # could do something like the following: # # def labelled_form_for(record_or_name_or_array, *args, &proc) # options = args.extract_options! # form_for(record_or_name_or_array, *(args << options.merge(:builder => LabellingFormBuilder)), &proc) # end # - # If you don't need to attach a form to a model instance, then check out FormTagHelper#form_tag. + # If you don't need to attach a form to a model instance, then check out + # FormTagHelper#form_tag. def form_for(record_or_name_or_array, *args, &proc) raise ArgumentError, "Missing block" unless block_given? @@ -910,6 +939,11 @@ module ActionView index = "" end + if options[:builder] + args << {} unless args.last.is_a?(Hash) + args.last[:builder] ||= options[:builder] + end + case record_or_name_or_array when String, Symbol if nested_attributes_association?(record_or_name_or_array) -- cgit v1.2.3 From 6de83562f91028629bd24447aa521bc72ef8277a Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 27 Feb 2009 14:22:39 +0100 Subject: Force all internal calls to Array#to_sentence to use English [#2010 state:resolved] --- actionpack/lib/action_controller/base.rb | 4 ++-- actionpack/lib/action_controller/request.rb | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 1eda6e3f04..5df94b289a 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -22,7 +22,7 @@ module ActionController #:nodoc: attr_reader :allowed_methods def initialize(*allowed_methods) - super("Only #{allowed_methods.to_sentence} requests are allowed.") + super("Only #{allowed_methods.to_sentence(:locale => :en)} requests are allowed.") @allowed_methods = allowed_methods end @@ -1298,7 +1298,7 @@ module ActionController #:nodoc: rescue ActionView::MissingTemplate => e # Was the implicit template missing, or was it another template? if e.path == default_template_name - raise UnknownAction, "No action responded to #{action_name}. Actions: #{action_methods.sort.to_sentence}", caller + raise UnknownAction, "No action responded to #{action_name}. Actions: #{action_methods.sort.to_sentence(:locale => :en)}", caller else raise e end diff --git a/actionpack/lib/action_controller/request.rb b/actionpack/lib/action_controller/request.rb index 0e95cfc147..2cabab9ec8 100755 --- a/actionpack/lib/action_controller/request.rb +++ b/actionpack/lib/action_controller/request.rb @@ -32,7 +32,7 @@ module ActionController # :get. If the request \method is not listed in the HTTP_METHODS # constant above, an UnknownHttpMethod exception is raised. def request_method - @request_method ||= HTTP_METHOD_LOOKUP[super] || raise(UnknownHttpMethod, "#{super}, accepted HTTP methods are #{HTTP_METHODS.to_sentence}") + @request_method ||= HTTP_METHOD_LOOKUP[super] || raise(UnknownHttpMethod, "#{super}, accepted HTTP methods are #{HTTP_METHODS.to_sentence(:locale => :en)}") end # Returns the HTTP request \method used for action processing as a -- cgit v1.2.3 From 77b0994c7835610982d708ce7ce5cd95e6e99e5a Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 27 Feb 2009 14:46:23 +0100 Subject: Prep for RC2 later today --- actionpack/lib/action_pack/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_pack/version.rb b/actionpack/lib/action_pack/version.rb index f20e44a7d5..f03a2a7605 100644 --- a/actionpack/lib/action_pack/version.rb +++ b/actionpack/lib/action_pack/version.rb @@ -2,7 +2,7 @@ module ActionPack #:nodoc: module VERSION #:nodoc: MAJOR = 2 MINOR = 3 - TINY = 0 + TINY = 1 STRING = [MAJOR, MINOR, TINY].join('.') end -- cgit v1.2.3 From f2a32bd0dedf11021027e36cc2c99f97434cae17 Mon Sep 17 00:00:00 2001 From: Gregg Pollack Date: Fri, 27 Feb 2009 13:24:52 -0500 Subject: Added ability to pass in :public => true to fresh_when, stale?, and expires_in to make the request proxy cachable [#2095 state:committed] Signed-off-by: David Heinemeier Hansson --- actionpack/lib/action_controller/base.rb | 42 ++++++++++++++++++++++++++------ 1 file changed, 35 insertions(+), 7 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 5df94b289a..564fdf677e 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -1133,6 +1133,11 @@ module ActionController #:nodoc: # request is considered stale and should be generated from scratch. Otherwise, # it's fresh and we don't need to generate anything and a reply of "304 Not Modified" is sent. # + # Parameters: + # * :etag + # * :last_modified + # * :public By default the Cache-Control header is private, set this to true if you want your application to be cachable by other devices (proxy caches). + # # Example: # # def show @@ -1153,20 +1158,34 @@ module ActionController #:nodoc: # Sets the etag, last_modified, or both on the response and renders a # "304 Not Modified" response if the request is already fresh. # + # Parameters: + # * :etag + # * :last_modified + # * :public By default the Cache-Control header is private, set this to true if you want your application to be cachable by other devices (proxy caches). + # # Example: # # def show # @article = Article.find(params[:id]) - # fresh_when(:etag => @article, :last_modified => @article.created_at.utc) + # fresh_when(:etag => @article, :last_modified => @article.created_at.utc, :public => true) # end # # This will render the show template if the request isn't sending a matching etag or # If-Modified-Since header and just a "304 Not Modified" response if there's a match. + # def fresh_when(options) - options.assert_valid_keys(:etag, :last_modified) + options.assert_valid_keys(:etag, :last_modified, :public) response.etag = options[:etag] if options[:etag] response.last_modified = options[:last_modified] if options[:last_modified] + + if options[:public] + cache_control = response.headers["Cache-Control"].split(",").map {|k| k.strip } + cache_control.delete("private") + cache_control.delete("no-cache") + cache_control << "public" + response.headers["Cache-Control"] = cache_control.join(', ') + end if request.fresh?(response) head :not_modified @@ -1178,15 +1197,24 @@ module ActionController #:nodoc: # # Examples: # expires_in 20.minutes - # expires_in 3.hours, :private => false - # expires in 3.hours, 'max-stale' => 5.hours, :private => nil, :public => true + # expires_in 3.hours, :public => true + # expires in 3.hours, 'max-stale' => 5.hours, :public => true # # This method will overwrite an existing Cache-Control header. # See http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html for more possibilities. def expires_in(seconds, options = {}) #:doc: - cache_options = { 'max-age' => seconds, 'private' => true }.symbolize_keys.merge!(options.symbolize_keys) - cache_options.delete_if { |k,v| v.nil? or v == false } - cache_control = cache_options.map{ |k,v| v == true ? k.to_s : "#{k.to_s}=#{v.to_s}"} + cache_control = response.headers["Cache-Control"].split(",").map {|k| k.strip } + + cache_control << "max-age=#{seconds}" + if options[:public] + cache_control.delete("private") + cache_control.delete("no-cache") + cache_control << "public" + end + + # This allows for additional headers to be passed through like 'max-stale' => 5.hours + cache_control += options.symbolize_keys.reject{|k,v| k == :public || k == :private }.map{ |k,v| v == true ? k.to_s : "#{k.to_s}=#{v.to_s}"} + response.headers["Cache-Control"] = cache_control.join(', ') end -- cgit v1.2.3 From 8607740a29d0f9ceb2ca21c9ef714f74b64d4a88 Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Sat, 28 Feb 2009 17:42:15 +0000 Subject: Ensure the old behaviour is retained when action_view.cache_template_loading is not set explicitly --- actionpack/lib/action_view/base.rb | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index 65b2062337..c373afeac0 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -183,12 +183,12 @@ module ActionView #:nodoc: cattr_accessor :debug_rjs # Specify whether templates should be cached. Otherwise the file we be read everytime it is accessed. - # Automaticaly reloading templates are not thread safe and should only be used in development mode. - @@cache_template_loading = false + # Automatically reloading templates are not thread safe and should only be used in development mode. + @@cache_template_loading = nil cattr_accessor :cache_template_loading def self.cache_template_loading? - ActionController::Base.allow_concurrency || cache_template_loading + ActionController::Base.allow_concurrency || cache_template_loading || !ActiveSupport::Dependencies.load? end attr_internal :request -- cgit v1.2.3 From 5029210914059faa65358b98a9c033a40e803c54 Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Sat, 28 Feb 2009 19:03:41 +0000 Subject: Use Array.wrap() instead of Array() and handle action_view.cache_template_loading being false --- actionpack/lib/action_view/base.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index c373afeac0..fe6053e574 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -188,7 +188,7 @@ module ActionView #:nodoc: cattr_accessor :cache_template_loading def self.cache_template_loading? - ActionController::Base.allow_concurrency || cache_template_loading || !ActiveSupport::Dependencies.load? + ActionController::Base.allow_concurrency || (cache_template_loading.nil? ? !ActiveSupport::Dependencies.load? : cache_template_loading) end attr_internal :request -- cgit v1.2.3 From ce56c5daa81d61a745b88220014a846a0eea46a4 Mon Sep 17 00:00:00 2001 From: Mike Gunderloy Date: Tue, 3 Mar 2009 17:40:39 -0600 Subject: Allow routes with a trailing slash to be recognized Signed-off-by: Michael Koziarski [#2039 state:committed] --- actionpack/lib/action_controller/routing/segments.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing/segments.rb b/actionpack/lib/action_controller/routing/segments.rb index cbb1a9c09a..358b4a6487 100644 --- a/actionpack/lib/action_controller/routing/segments.rb +++ b/actionpack/lib/action_controller/routing/segments.rb @@ -318,7 +318,7 @@ module ActionController end def regexp_chunk - '(\.[^/?\.]+)?' + '/|(\.[^/?\.]+)?' end def to_s -- cgit v1.2.3 From 638b3b15a13c4e274cfb317c40248e9feea3bfae Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Wed, 4 Mar 2009 14:37:59 -0600 Subject: Generating routes with optional format segment does not inherit params format [#2043 state:resolved] --- actionpack/lib/action_controller/routing/segments.rb | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing/segments.rb b/actionpack/lib/action_controller/routing/segments.rb index 358b4a6487..4f936d51d2 100644 --- a/actionpack/lib/action_controller/routing/segments.rb +++ b/actionpack/lib/action_controller/routing/segments.rb @@ -324,7 +324,11 @@ module ActionController def to_s '(.:format)?' end - + + def extract_value + "#{local_name} = options[:#{key}] && options[:#{key}].to_s.downcase" + end + #the value should not include the period (.) def match_extraction(next_capture) %[ -- cgit v1.2.3 From b1c989f28dd1d619f0e3e3ca1b894b686e517f2f Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 5 Mar 2009 12:22:49 +0100 Subject: Fixed that redirection would just log the options, not the final url (which lead to "Redirected to #") [DHH] --- actionpack/lib/action_controller/base.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 564fdf677e..b769a2e67e 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -1101,7 +1101,6 @@ module ActionController #:nodoc: end response.redirected_to = options - logger.info("Redirected to #{options}") if logger && logger.info? case options # The scheme name consist of a letter followed by any combination of @@ -1124,6 +1123,7 @@ module ActionController #:nodoc: def redirect_to_full_url(url, status) raise DoubleRenderError if performed? + logger.info("Redirected to #{url}") if logger && logger.info? response.redirect(url, interpret_status(status)) @performed_redirect = true end -- cgit v1.2.3 From 5b7527ca44521edf9782b3d7f449bf09a29267f2 Mon Sep 17 00:00:00 2001 From: Mike Gunderloy Date: Thu, 5 Mar 2009 18:46:59 -0600 Subject: Failing test for routes with member & requirement [#2054 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_controller/resources.rb | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/resources.rb b/actionpack/lib/action_controller/resources.rb index 3af21967df..8195b38685 100644 --- a/actionpack/lib/action_controller/resources.rb +++ b/actionpack/lib/action_controller/resources.rb @@ -670,7 +670,12 @@ module ActionController when "show", "edit"; default_options.merge(add_conditions_for(resource.conditions, method || :get)).merge(resource.requirements(require_id)) when "update"; default_options.merge(add_conditions_for(resource.conditions, method || :put)).merge(resource.requirements(require_id)) when "destroy"; default_options.merge(add_conditions_for(resource.conditions, method || :delete)).merge(resource.requirements(require_id)) - else default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) + else + if method.nil? || resource.member_methods.nil? || resource.member_methods[method.to_sym].nil? + default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) + else + resource.member_methods[method.to_sym].include?(action) ? default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements(require_id)) : default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) + end end end end -- cgit v1.2.3 From 3191535ff0912e751dcf411c57923ec79b72944d Mon Sep 17 00:00:00 2001 From: thedarkone Date: Thu, 5 Mar 2009 18:49:22 -0600 Subject: Fix layouts with absolute paths [#2134 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_controller/base.rb | 1 - 1 file changed, 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index b769a2e67e..5da47ce317 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -913,7 +913,6 @@ module ActionController #:nodoc: layout = pick_layout(options) response.layout = layout.path_without_format_and_extension if layout logger.info("Rendering template within #{layout.path_without_format_and_extension}") if logger && layout - layout = layout.path_without_format_and_extension if layout if content_type = options[:content_type] response.content_type = content_type.to_s -- cgit v1.2.3 From cb40c761b2ac1c82e6fb0e777eb48426a9dfa055 Mon Sep 17 00:00:00 2001 From: Niels Ganser Date: Fri, 6 Mar 2009 13:45:26 +0100 Subject: Minor spelling fix --- actionpack/lib/action_controller/integration.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/integration.rb b/actionpack/lib/action_controller/integration.rb index 1c05ab0bf6..26b695570b 100644 --- a/actionpack/lib/action_controller/integration.rb +++ b/actionpack/lib/action_controller/integration.rb @@ -5,7 +5,7 @@ require 'active_support/test_case' module ActionController module Integration #:nodoc: # An integration Session instance represents a set of requests and responses - # performed sequentially by some virtual user. Becase you can instantiate + # performed sequentially by some virtual user. Because you can instantiate # multiple sessions and run them side-by-side, you can also mimic (to some # limited extent) multiple simultaneous users interacting with your system. # -- cgit v1.2.3 From c071123b3e2d6fd918dd7e419efe7429355445c2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Johan=20S=C3=B8rensen?= Date: Fri, 6 Mar 2009 10:17:20 +0100 Subject: Ensure expires_in without a :public key sets the Cache-Control header to private. [#2095 state:resolved] This fixes a regression introduced in f2a32bd0, which wasn't exposed due to two test methods having the same name. Signed-off-by: Pratik Naik --- actionpack/lib/action_controller/base.rb | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 5da47ce317..9d06d052b4 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -1205,10 +1205,12 @@ module ActionController #:nodoc: cache_control = response.headers["Cache-Control"].split(",").map {|k| k.strip } cache_control << "max-age=#{seconds}" + cache_control.delete("no-cache") if options[:public] cache_control.delete("private") - cache_control.delete("no-cache") cache_control << "public" + else + cache_control << "private" end # This allows for additional headers to be passed through like 'max-stale' => 5.hours -- cgit v1.2.3 From a0bb8bcb166a9d66c81fd68b8c128fb06d6c725d Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Sat, 7 Mar 2009 15:53:09 +0000 Subject: =?UTF-8?q?Remove=20unused=20variable=20[#1451=20state:resolved]?= =?UTF-8?q?=20[Rapha=C3=ABl=20Valyi]?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- actionpack/lib/action_controller/routing/recognition_optimisation.rb | 1 - 1 file changed, 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing/recognition_optimisation.rb b/actionpack/lib/action_controller/routing/recognition_optimisation.rb index ebc553512f..9bfebff0c0 100644 --- a/actionpack/lib/action_controller/routing/recognition_optimisation.rb +++ b/actionpack/lib/action_controller/routing/recognition_optimisation.rb @@ -98,7 +98,6 @@ module ActionController if Array === item i += 1 start = (i == 1) - final = (i == list.size) tag, sub = item if tag == :dynamic body += padding + "#{start ? 'if' : 'elsif'} true\n" -- cgit v1.2.3 From 272c2d2e9ca38a307878306bff4315183d1ae7ab Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Sat, 7 Mar 2009 16:13:34 +0000 Subject: Ensure assert_select works with XML namespaced attributes [#1547 state:resolved] [Jon Yurek] --- actionpack/lib/action_controller/vendor/html-scanner/html/selector.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/html-scanner/html/selector.rb b/actionpack/lib/action_controller/vendor/html-scanner/html/selector.rb index 376bb87409..e2c49c284f 100644 --- a/actionpack/lib/action_controller/vendor/html-scanner/html/selector.rb +++ b/actionpack/lib/action_controller/vendor/html-scanner/html/selector.rb @@ -556,7 +556,7 @@ module HTML end # Attribute value. - next if statement.sub!(/^\[\s*([[:alpha:]][\w\-]*)\s*((?:[~|^$*])?=)?\s*('[^']*'|"[^*]"|[^\]]*)\s*\]/) do |match| + next if statement.sub!(/^\[\s*([[:alpha:]][\w\-:]*)\s*((?:[~|^$*])?=)?\s*('[^']*'|"[^*]"|[^\]]*)\s*\]/) do |match| name, equality, value = $1, $2, $3 if value == "?" value = values.shift -- cgit v1.2.3 From 45494580d9405e80ba124d17c8379436883c8c78 Mon Sep 17 00:00:00 2001 From: Dan Barry Date: Sat, 7 Mar 2009 18:55:12 +0000 Subject: =?UTF-8?q?Ensure=20Active=20Record=20error=20related=20view=20hel?= =?UTF-8?q?pers=20escape=20the=20message=20[#1280=20state:resolved]=20[Ing?= =?UTF-8?q?e=20J=C3=B8rgensen,=20Dan=20Barry]?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Pratik Naik --- actionpack/lib/action_view/helpers/active_record_helper.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/active_record_helper.rb b/actionpack/lib/action_view/helpers/active_record_helper.rb index 8b56d241ae..541899ea6a 100644 --- a/actionpack/lib/action_view/helpers/active_record_helper.rb +++ b/actionpack/lib/action_view/helpers/active_record_helper.rb @@ -121,7 +121,7 @@ module ActionView if (obj = (object.respond_to?(:errors) ? object : instance_variable_get("@#{object}"))) && (errors = obj.errors.on(method)) content_tag("div", - "#{options[:prepend_text]}#{errors.is_a?(Array) ? errors.first : errors}#{options[:append_text]}", + "#{options[:prepend_text]}#{ERB::Util.html_escape(errors.is_a?(Array) ? errors.first : errors)}#{options[:append_text]}", :class => options[:css_class] ) else @@ -198,7 +198,7 @@ module ActionView locale.t :header, :count => count, :model => object_name end message = options.include?(:message) ? options[:message] : locale.t(:body) - error_messages = objects.sum {|object| object.errors.full_messages.map {|msg| content_tag(:li, msg) } }.join + error_messages = objects.sum {|object| object.errors.full_messages.map {|msg| content_tag(:li, ERB::Util.html_escape(msg)) } }.join contents = '' contents << content_tag(options[:header_tag] || :h2, header_message) unless header_message.blank? -- cgit v1.2.3 From 77f7d98e38dddf72890c80b4e4b2e088bb76d111 Mon Sep 17 00:00:00 2001 From: Lawrence Pit Date: Sat, 7 Mar 2009 13:29:35 -0600 Subject: submit_tag with confirmation and disable_with [#660 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_view/helpers/form_tag_helper.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/form_tag_helper.rb b/actionpack/lib/action_view/helpers/form_tag_helper.rb index 4646bc118b..6d39a53adc 100644 --- a/actionpack/lib/action_view/helpers/form_tag_helper.rb +++ b/actionpack/lib/action_view/helpers/form_tag_helper.rb @@ -360,8 +360,8 @@ module ActionView end if confirm = options.delete("confirm") - options["onclick"] ||= '' - options["onclick"] << "return #{confirm_javascript_function(confirm)};" + options["onclick"] ||= 'return true;' + options["onclick"] = "if (!#{confirm_javascript_function(confirm)}) return false; #{options['onclick']}" end tag :input, { "type" => "submit", "name" => "commit", "value" => value }.update(options.stringify_keys) -- cgit v1.2.3 From 87e8b162463f13bd50d27398f020769460a770e3 Mon Sep 17 00:00:00 2001 From: Matt Jones Date: Sat, 7 Mar 2009 13:32:46 -0600 Subject: fix HTML fallback for explicit templates [#2052 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_controller/layout.rb | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/layout.rb b/actionpack/lib/action_controller/layout.rb index ccd9605562..6ec0c1b304 100644 --- a/actionpack/lib/action_controller/layout.rb +++ b/actionpack/lib/action_controller/layout.rb @@ -198,7 +198,7 @@ module ActionController #:nodoc: # is called and the return value is used. Likewise if the layout was specified as an inline method (through a proc or method # object). If the layout was defined without a directory, layouts is assumed. So layout "weblog/standard" will return # weblog/standard, but layout "standard" will return layouts/standard. - def active_layout(passed_layout = nil) + def active_layout(passed_layout = nil, options = {}) layout = passed_layout || default_layout return layout if layout.respond_to?(:render) @@ -208,7 +208,7 @@ module ActionController #:nodoc: else layout end - find_layout(active_layout, default_template_format) if active_layout + find_layout(active_layout, default_template_format, options[:html_fallback]) if active_layout end private @@ -220,8 +220,8 @@ module ActionController #:nodoc: nil end - def find_layout(layout, format) #:nodoc: - view_paths.find_template(layout.to_s =~ /layouts\// ? layout : "layouts/#{layout}", format, false) + def find_layout(layout, format, html_fallback=false) #:nodoc: + view_paths.find_template(layout.to_s =~ /layouts\// ? layout : "layouts/#{layout}", format, html_fallback) rescue ActionView::MissingTemplate raise if Mime::Type.lookup_by_extension(format.to_s).html? end @@ -234,7 +234,7 @@ module ActionController #:nodoc: when NilClass, TrueClass active_layout if action_has_layout? && candidate_for_layout?(:template => default_template_name) else - active_layout(layout) + active_layout(layout, :html_fallback => true) end else active_layout if action_has_layout? && candidate_for_layout?(options) -- cgit v1.2.3 From ea8488caef77cb8cf2031d344e74981ab6ea0e57 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Sat, 7 Mar 2009 14:05:18 -0600 Subject: Fixed simplified render with nested models [#2042 state:resolved] --- actionpack/lib/action_controller/base.rb | 3 +++ 1 file changed, 3 insertions(+) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 9d06d052b4..0facf7066d 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -907,6 +907,9 @@ module ActionController #:nodoc: extra_options[:template] = options end + options = extra_options + elsif !options.is_a?(Hash) + extra_options[:partial] = options options = extra_options end -- cgit v1.2.3 From 5c87e9adddc22703a3dbbb785e32fafe0e91ce78 Mon Sep 17 00:00:00 2001 From: Tom Stuart Date: Sat, 7 Mar 2009 22:50:58 +0000 Subject: Ensure shallow routes respects namespace [#1356 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_controller/resources.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/resources.rb b/actionpack/lib/action_controller/resources.rb index 8195b38685..0a89c4b3d5 100644 --- a/actionpack/lib/action_controller/resources.rb +++ b/actionpack/lib/action_controller/resources.rb @@ -91,7 +91,7 @@ module ActionController end def shallow_path_prefix - @shallow_path_prefix ||= "#{path_prefix unless @options[:shallow]}" + @shallow_path_prefix ||= @options[:shallow] ? @options[:namespace].try(:sub, /\/$/, '') : path_prefix end def member_path @@ -103,7 +103,7 @@ module ActionController end def shallow_name_prefix - @shallow_name_prefix ||= "#{name_prefix unless @options[:shallow]}" + @shallow_name_prefix ||= @options[:shallow] ? @options[:namespace].try(:gsub, /\//, '_') : name_prefix end def nesting_name_prefix -- cgit v1.2.3 From 5e0f6214d2421a4931c85ee6a239158c69e57b65 Mon Sep 17 00:00:00 2001 From: Mike Gunderloy Date: Sun, 8 Mar 2009 07:31:27 -0500 Subject: Support OPTIONS verb in route conditions [#1727 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_controller/routing.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing.rb b/actionpack/lib/action_controller/routing.rb index a2141a77dc..c0eb61340b 100644 --- a/actionpack/lib/action_controller/routing.rb +++ b/actionpack/lib/action_controller/routing.rb @@ -267,7 +267,7 @@ module ActionController module Routing SEPARATORS = %w( / . ? ) - HTTP_METHODS = [:get, :head, :post, :put, :delete] + HTTP_METHODS = [:get, :head, :post, :put, :delete, :options] ALLOWED_REQUIREMENTS_FOR_OPTIMISATION = [:controller, :action].to_set -- cgit v1.2.3 From a3e67a15edcdcfd2fd84f078cb3e2c76d0226794 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Sun, 8 Mar 2009 13:41:51 -0700 Subject: Prototype helpers support the onCreate callback. [#1074 state:committed] --- actionpack/lib/action_view/helpers/prototype_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/prototype_helper.rb b/actionpack/lib/action_view/helpers/prototype_helper.rb index 18a209dcea..91ef72e54b 100644 --- a/actionpack/lib/action_view/helpers/prototype_helper.rb +++ b/actionpack/lib/action_view/helpers/prototype_helper.rb @@ -107,7 +107,7 @@ module ActionView # on the page in an Ajax response. module PrototypeHelper unless const_defined? :CALLBACKS - CALLBACKS = Set.new([ :uninitialized, :loading, :loaded, + CALLBACKS = Set.new([ :create, :uninitialized, :loading, :loaded, :interactive, :complete, :failure, :success ] + (100..599).to_a) AJAX_OPTIONS = Set.new([ :before, :after, :condition, :url, -- cgit v1.2.3 From 1ab2ff58eddee8ac523624dd097424f9a760ad8b Mon Sep 17 00:00:00 2001 From: rpheath Date: Sun, 8 Mar 2009 23:52:28 -0400 Subject: Fixed number_to_phone to work with 7 digit numbers [#2176 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_view/helpers/number_helper.rb | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/number_helper.rb b/actionpack/lib/action_view/helpers/number_helper.rb index e622f97b9e..539f43c6e3 100644 --- a/actionpack/lib/action_view/helpers/number_helper.rb +++ b/actionpack/lib/action_view/helpers/number_helper.rb @@ -15,6 +15,7 @@ module ActionView # * :country_code - Sets the country code for the phone number. # # ==== Examples + # number_to_phone(5551234) # => 555-1234 # number_to_phone(1235551234) # => 123-555-1234 # number_to_phone(1235551234, :area_code => true) # => (123) 555-1234 # number_to_phone(1235551234, :delimiter => " ") # => 123 555 1234 @@ -37,7 +38,8 @@ module ActionView str << if area_code number.gsub!(/([0-9]{1,3})([0-9]{3})([0-9]{4}$)/,"(\\1) \\2#{delimiter}\\3") else - number.gsub!(/([0-9]{1,3})([0-9]{3})([0-9]{4})$/,"\\1#{delimiter}\\2#{delimiter}\\3") + number.gsub!(/([0-9]{0,3})([0-9]{3})([0-9]{4})$/,"\\1#{delimiter}\\2#{delimiter}\\3") + number.starts_with?('-') ? number.slice!(1..-1) : number end str << " x #{extension}" unless extension.blank? str -- cgit v1.2.3 From 90dba00822acd1e01f7a39625668ee74ffe5f061 Mon Sep 17 00:00:00 2001 From: Andrew Bloom Date: Mon, 9 Mar 2009 15:27:13 +0000 Subject: Ensure blank path_prefix works as expected [#2122 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_controller/routing/builder.rb | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/routing/builder.rb b/actionpack/lib/action_controller/routing/builder.rb index 44d759444a..d9590c88b8 100644 --- a/actionpack/lib/action_controller/routing/builder.rb +++ b/actionpack/lib/action_controller/routing/builder.rb @@ -159,7 +159,8 @@ module ActionController path = "/#{path}" unless path[0] == ?/ path = "#{path}/" unless path[-1] == ?/ - path = "/#{options[:path_prefix].to_s.gsub(/^\//,'')}#{path}" if options[:path_prefix] + prefix = options[:path_prefix].to_s.gsub(/^\//,'') + path = "/#{prefix}#{path}" unless prefix.blank? segments = segments_for_route_path(path) defaults, requirements, conditions = divide_route_options(segments, options) -- cgit v1.2.3 From 224a534400fd622dda57058d1eed349b8375e5e3 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Mon, 9 Mar 2009 22:45:38 -0500 Subject: reset_session should force a new session id to be generated [#2173] --- actionpack/lib/action_controller/request.rb | 1 + 1 file changed, 1 insertion(+) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/request.rb b/actionpack/lib/action_controller/request.rb index 2cabab9ec8..ef223f157c 100755 --- a/actionpack/lib/action_controller/request.rb +++ b/actionpack/lib/action_controller/request.rb @@ -442,6 +442,7 @@ EOM end def reset_session + @env['rack.session.options'].delete(:id) @env['rack.session'] = {} end -- cgit v1.2.3 From bdfa733d04c5843eadc181f2fd1723db614fc3d0 Mon Sep 17 00:00:00 2001 From: Eugene Pimenov Date: Tue, 10 Mar 2009 16:52:21 +0000 Subject: Ensure auto_link doesnt linkify URLs in the middle of a tag [#1523 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_view/helpers/text_helper.rb | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/text_helper.rb b/actionpack/lib/action_view/helpers/text_helper.rb index 63fe0c1c57..48bf4717ad 100644 --- a/actionpack/lib/action_view/helpers/text_helper.rb +++ b/actionpack/lib/action_view/helpers/text_helper.rb @@ -536,8 +536,9 @@ module ActionView text.gsub(AUTO_LINK_RE) do href = $& punctuation = '' - # detect already linked URLs - if $` =~ /]*href="$/ + left, right = $`, $' + # detect already linked URLs and URLs in the middle of a tag + if left =~ /<[^>]+$/ && right =~ /^[^>]*>/ # do not change string; URL is alreay linked href else -- cgit v1.2.3 From 572e0aac802334d2029e67eb1e87356d890f4255 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Tue, 10 Mar 2009 15:05:38 -0500 Subject: update bundled version of rack before 2.3 final --- .../lib/action_controller/vendor/rack-1.0/rack.rb | 1 + .../vendor/rack-1.0/rack/auth/abstract/handler.rb | 4 ++-- .../vendor/rack-1.0/rack/auth/digest/md5.rb | 2 +- .../vendor/rack-1.0/rack/auth/digest/request.rb | 2 +- .../vendor/rack-1.0/rack/builder.rb | 6 +----- .../vendor/rack-1.0/rack/content_type.rb | 23 ++++++++++++++++++++++ .../vendor/rack-1.0/rack/directory.rb | 2 ++ .../vendor/rack-1.0/rack/handler/webrick.rb | 7 ++++++- .../action_controller/vendor/rack-1.0/rack/lint.rb | 4 +++- .../vendor/rack-1.0/rack/response.rb | 2 ++ 10 files changed, 42 insertions(+), 11 deletions(-) create mode 100644 actionpack/lib/action_controller/vendor/rack-1.0/rack/content_type.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb index 6c03b55552..e3e20ed2a3 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb @@ -31,6 +31,7 @@ module Rack autoload :CommonLogger, "rack/commonlogger" autoload :ConditionalGet, "rack/conditionalget" autoload :ContentLength, "rack/content_length" + autoload :ContentType, "rack/content_type" autoload :File, "rack/file" autoload :Deflater, "rack/deflater" autoload :Directory, "rack/directory" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/abstract/handler.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/abstract/handler.rb index 8489c9b9c4..214df6299e 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/abstract/handler.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/abstract/handler.rb @@ -8,8 +8,8 @@ module Rack attr_accessor :realm - def initialize(app, &authenticator) - @app, @authenticator = app, authenticator + def initialize(app, realm=nil, &authenticator) + @app, @realm, @authenticator = app, realm, authenticator end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/md5.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/md5.rb index 6d2bd29c2e..e579dc9632 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/md5.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/md5.rb @@ -21,7 +21,7 @@ module Rack attr_writer :passwords_hashed - def initialize(app) + def initialize(*args) super @passwords_hashed = nil end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/request.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/request.rb index a40f57b7f1..a8aa3bf996 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/request.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/auth/digest/request.rb @@ -8,7 +8,7 @@ module Rack class Request < Auth::AbstractRequest def method - @env['REQUEST_METHOD'] + @env['rack.methodoverride.original_method'] || @env['REQUEST_METHOD'] end def digest? diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/builder.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/builder.rb index 25994d5a44..295235e56a 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/builder.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/builder.rb @@ -34,11 +34,7 @@ module Rack end def use(middleware, *args, &block) - @ins << if block_given? - lambda { |app| middleware.new(app, *args, &block) } - else - lambda { |app| middleware.new(app, *args) } - end + @ins << lambda { |app| middleware.new(app, *args, &block) } end def run(app) diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_type.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_type.rb new file mode 100644 index 0000000000..0c1e1ca3e1 --- /dev/null +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_type.rb @@ -0,0 +1,23 @@ +require 'rack/utils' + +module Rack + + # Sets the Content-Type header on responses which don't have one. + # + # Builder Usage: + # use Rack::ContentType, "text/plain" + # + # When no content type argument is provided, "text/html" is assumed. + class ContentType + def initialize(app, content_type = "text/html") + @app, @content_type = app, content_type + end + + def call(env) + status, headers, body = @app.call(env) + headers = Utils::HeaderHash.new(headers) + headers['Content-Type'] ||= @content_type + [status, headers.to_hash, body] + end + end +end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb index 56ee5e7b60..0f37df3a86 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb @@ -89,6 +89,8 @@ table { width:100%%; } type = stat.directory? ? 'directory' : Mime.mime_type(ext) size = stat.directory? ? '-' : filesize_format(size) mtime = stat.mtime.httpdate + url << '/' if stat.directory? + basename << '/' if stat.directory? @files << [ url, basename, size, type, mtime ] end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb index 40be79de13..138aae0ee9 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb @@ -35,7 +35,12 @@ module Rack env["HTTP_VERSION"] ||= env["SERVER_PROTOCOL"] env["QUERY_STRING"] ||= "" env["REQUEST_PATH"] ||= "/" - env.delete "PATH_INFO" if env["PATH_INFO"] == "" + if env["PATH_INFO"] == "" + env.delete "PATH_INFO" + else + path, n = req.request_uri.path, env["SCRIPT_NAME"].length + env["PATH_INFO"] = path[n, path.length-n] + end status, headers, body = @app.call(env) begin diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb index 7eb05437f0..66d252b8b0 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb @@ -88,7 +88,9 @@ module Rack ## within the application. This may be an ## empty string, if the request URL targets ## the application root and does not have a - ## trailing slash. + ## trailing slash. This information should be + ## decoded by the server if it comes from a + ## URL. ## QUERY_STRING:: The portion of the request URL that ## follows the ?, if any. May be diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/response.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/response.rb index a593110139..caf60d5b19 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/response.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/response.rb @@ -16,6 +16,8 @@ module Rack # Your application's +call+ should end returning Response#finish. class Response + attr_accessor :length + def initialize(body=[], status=200, header={}, &block) @status = status @header = Utils::HeaderHash.new({"Content-Type" => "text/html"}. -- cgit v1.2.3 From 0a887e2386a827f554c685dccf91701bb38422b5 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Tue, 10 Mar 2009 15:09:44 -0500 Subject: check for rack 1.0 gem before falling back to bundled version --- actionpack/lib/action_controller.rb | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller.rb b/actionpack/lib/action_controller.rb index ca826e7bfc..d03f4cb231 100644 --- a/actionpack/lib/action_controller.rb +++ b/actionpack/lib/action_controller.rb @@ -31,7 +31,12 @@ rescue LoadError end end -require 'action_controller/vendor/rack-1.0/rack' +begin + gem 'rack', '~> 1.0.0' + require 'rack' +rescue Gem::LoadError + require 'action_controller/vendor/rack-1.0/rack' +end module ActionController # TODO: Review explicit to see if they will automatically be handled by -- cgit v1.2.3 From fa45540cdb30cee44983c9121e3ebfc317d21668 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mislav=20Marohni=C4=87?= Date: Wed, 11 Mar 2009 00:02:08 +0100 Subject: Ensure correct content type is declared after cache hits on actions with string cache keys [#1585 state:resolved] Signed-off-by: Pratik Naik --- .../lib/action_controller/caching/actions.rb | 27 ++++++++-------------- 1 file changed, 10 insertions(+), 17 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/caching/actions.rb b/actionpack/lib/action_controller/caching/actions.rb index 34e1c3527f..87b5029e57 100644 --- a/actionpack/lib/action_controller/caching/actions.rb +++ b/actionpack/lib/action_controller/caching/actions.rb @@ -129,24 +129,23 @@ module ActionController #:nodoc: attr_reader :path, :extension class << self - def path_for(controller, options, infer_extension=true) + def path_for(controller, options, infer_extension = true) new(controller, options, infer_extension).path end end # When true, infer_extension will look up the cache path extension from the request's path & format. - # This is desirable when reading and writing the cache, but not when expiring the cache - expire_action should expire the same files regardless of the request format. - def initialize(controller, options = {}, infer_extension=true) - if infer_extension and options.is_a? Hash - request_extension = extract_extension(controller.request) - options = options.reverse_merge(:format => request_extension) + # This is desirable when reading and writing the cache, but not when expiring the cache - + # expire_action should expire the same files regardless of the request format. + def initialize(controller, options = {}, infer_extension = true) + if infer_extension + extract_extension(controller.request) + options = options.reverse_merge(:format => @extension) if options.is_a?(Hash) end + path = controller.url_for(options).split('://').last normalize!(path) - if infer_extension - @extension = request_extension - add_extension!(path, @extension) - end + add_extension!(path, @extension) @path = URI.unescape(path) end @@ -162,13 +161,7 @@ module ActionController #:nodoc: def extract_extension(request) # Don't want just what comes after the last '.' to accommodate multi part extensions # such as tar.gz. - extension = request.path[/^[^.]+\.(.+)$/, 1] - - # If there's no extension in the path, check request.format - if extension.nil? - extension = request.cache_format - end - extension + @extension = request.path[/^[^.]+\.(.+)$/, 1] || request.cache_format end end end -- cgit v1.2.3 From f2c7508befb085ffe19ec7fb9ca2e6919cc919c9 Mon Sep 17 00:00:00 2001 From: Russ Smith Date: Wed, 11 Mar 2009 12:50:24 -0500 Subject: Update bundled Rack to fix Litespeed compatibility [#2198 state:resolved] Signed-off-by: Joshua Peek --- .../vendor/rack-1.0/rack/content_length.rb | 8 +++++--- .../lib/action_controller/vendor/rack-1.0/rack/deflater.rb | 4 ++-- .../lib/action_controller/vendor/rack-1.0/rack/directory.rb | 4 ++-- .../action_controller/vendor/rack-1.0/rack/handler/lsws.rb | 2 +- .../lib/action_controller/vendor/rack-1.0/rack/lint.rb | 2 +- .../action_controller/vendor/rack-1.0/rack/showstatus.rb | 2 +- .../lib/action_controller/vendor/rack-1.0/rack/utils.rb | 13 +++++++++++++ 7 files changed, 25 insertions(+), 10 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_length.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_length.rb index bce22a32c5..1e56d43853 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_length.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/content_length.rb @@ -3,21 +3,23 @@ require 'rack/utils' module Rack # Sets the Content-Length header on responses with fixed-length bodies. class ContentLength + include Rack::Utils + def initialize(app) @app = app end def call(env) status, headers, body = @app.call(env) - headers = Utils::HeaderHash.new(headers) + headers = HeaderHash.new(headers) - if !Utils::STATUS_WITH_NO_ENTITY_BODY.include?(status) && + if !STATUS_WITH_NO_ENTITY_BODY.include?(status) && !headers['Content-Length'] && !headers['Transfer-Encoding'] && (body.respond_to?(:to_ary) || body.respond_to?(:to_str)) body = [body] if body.respond_to?(:to_str) # rack 0.4 compat - length = body.to_ary.inject(0) { |len, part| len + part.length } + length = body.to_ary.inject(0) { |len, part| len + bytesize(part) } headers['Content-Length'] = length.to_s end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/deflater.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/deflater.rb index 3e66680092..a42b7477ae 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/deflater.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/deflater.rb @@ -36,12 +36,12 @@ module Rack mtime = headers.key?("Last-Modified") ? Time.httpdate(headers["Last-Modified"]) : Time.now body = self.class.gzip(body, mtime) - size = body.respond_to?(:bytesize) ? body.bytesize : body.size + size = Rack::Utils.bytesize(body) headers = headers.merge("Content-Encoding" => "gzip", "Content-Length" => size.to_s) [status, headers, [body]] when "deflate" body = self.class.deflate(body) - size = body.respond_to?(:bytesize) ? body.bytesize : body.size + size = Rack::Utils.bytesize(body) headers = headers.merge("Content-Encoding" => "deflate", "Content-Length" => size.to_s) [status, headers, [body]] when "identity" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb index 0f37df3a86..acdd3029d3 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/directory.rb @@ -70,7 +70,7 @@ table { width:100%%; } return unless @path_info.include? ".." body = "Forbidden\n" - size = body.respond_to?(:bytesize) ? body.bytesize : body.size + size = Rack::Utils.bytesize(body) return [403, {"Content-Type" => "text/plain","Content-Length" => size.to_s}, [body]] end @@ -122,7 +122,7 @@ table { width:100%%; } def entity_not_found body = "Entity not found: #{@path_info}\n" - size = body.respond_to?(:bytesize) ? body.bytesize : body.size + size = Rack::Utils.bytesize(body) return [404, {"Content-Type" => "text/plain", "Content-Length" => size.to_s}, [body]] end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb index 1f850fc77b..dfc79c204b 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb @@ -13,7 +13,7 @@ module Rack env.delete "HTTP_CONTENT_LENGTH" env["SCRIPT_NAME"] = "" if env["SCRIPT_NAME"] == "/" env.update({"rack.version" => [0,1], - "rack.input" => $stdin, + "rack.input" => StringIO.new($stdin.read.to_s), "rack.errors" => $stderr, "rack.multithread" => false, "rack.multiprocess" => true, diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb index 66d252b8b0..ec4dac96f8 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb @@ -403,7 +403,7 @@ module Rack break end - bytes += (part.respond_to?(:bytesize) ? part.bytesize : part.size) + bytes += Rack::Utils.bytesize(part) } if env["REQUEST_METHOD"] == "HEAD" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/showstatus.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/showstatus.rb index 5f13404dce..28258c7c89 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/showstatus.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/showstatus.rb @@ -27,7 +27,7 @@ module Rack message = Rack::Utils::HTTP_STATUS_CODES[status.to_i] || status.to_s detail = env["rack.showstatus.detail"] || message body = @template.result(binding) - size = body.respond_to?(:bytesize) ? body.bytesize : body.size + size = Rack::Utils.bytesize(body) [status, headers.merge("Content-Type" => "text/html", "Content-Length" => size.to_s), [body]] else [status, headers, body] diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb index f352cb6783..e86d4ccdcd 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb @@ -144,6 +144,19 @@ module Rack end module_function :select_best_encoding + # Return the bytesize of String; uses String#length under Ruby 1.8 and + # String#bytesize under 1.9. + if ''.respond_to?(:bytesize) + def bytesize(string) + string.bytesize + end + else + def bytesize(string) + string.size + end + end + module_function :bytesize + # Context allows the use of a compatible middleware at different points # in a request handling stack. A compatible middleware must define # #context which should take the arguments env and app. The first of which -- cgit v1.2.3 From 724eb9e6121b36e61f373ba4bdcce29f3d0c78da Mon Sep 17 00:00:00 2001 From: Henrik N Date: Thu, 12 Mar 2009 07:29:57 +0100 Subject: Fix some typos, including a global "seperator" -> "separator". --- actionpack/lib/action_view/helpers/date_helper.rb | 4 ++-- actionpack/lib/action_view/helpers/number_helper.rb | 2 +- actionpack/lib/action_view/helpers/text_helper.rb | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/date_helper.rb b/actionpack/lib/action_view/helpers/date_helper.rb index b7ef1fb90d..c74909a360 100644 --- a/actionpack/lib/action_view/helpers/date_helper.rb +++ b/actionpack/lib/action_view/helpers/date_helper.rb @@ -876,8 +876,8 @@ module ActionView input_name_from_type(type).gsub(/([\[\(])|(\]\[)/, '_').gsub(/[\]\)]/, '') end - # Given an ordering of datetime components, create the selection html - # and join them with their appropriate seperators + # Given an ordering of datetime components, create the selection HTML + # and join them with their appropriate separators. def build_selects_from_types(order) select = '' order.reverse.each do |type| diff --git a/actionpack/lib/action_view/helpers/number_helper.rb b/actionpack/lib/action_view/helpers/number_helper.rb index 539f43c6e3..dea958deaf 100644 --- a/actionpack/lib/action_view/helpers/number_helper.rb +++ b/actionpack/lib/action_view/helpers/number_helper.rb @@ -140,7 +140,7 @@ module ActionView # number_with_delimiter(12345678) # => 12,345,678 # number_with_delimiter(12345678.05) # => 12,345,678.05 # number_with_delimiter(12345678, :delimiter => ".") # => 12.345.678 - # number_with_delimiter(12345678, :seperator => ",") # => 12,345,678 + # number_with_delimiter(12345678, :separator => ",") # => 12,345,678 # number_with_delimiter(98765432.98, :delimiter => " ", :separator => ",") # # => 98 765 432,98 # diff --git a/actionpack/lib/action_view/helpers/text_helper.rb b/actionpack/lib/action_view/helpers/text_helper.rb index 63fe0c1c57..feeddba78d 100644 --- a/actionpack/lib/action_view/helpers/text_helper.rb +++ b/actionpack/lib/action_view/helpers/text_helper.rb @@ -538,7 +538,7 @@ module ActionView punctuation = '' # detect already linked URLs if $` =~ /]*href="$/ - # do not change string; URL is alreay linked + # do not change string; URL is already linked href else # don't include trailing punctuation character as part of the URL -- cgit v1.2.3 From be7b64b35aac1c9e9063d1d8317f8b1be2a3411c Mon Sep 17 00:00:00 2001 From: Donald Parish Date: Thu, 12 Mar 2009 13:24:54 +0000 Subject: Support MD5 passwords for Digest auth and use session_options[:secret] in nonce [#2209 state:resolved] Signed-off-by: Pratik Naik --- .../lib/action_controller/http_authentication.rb | 72 +++++++++++++++------- 1 file changed, 51 insertions(+), 21 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/http_authentication.rb b/actionpack/lib/action_controller/http_authentication.rb index 2ccbc22420..b6b5267c66 100644 --- a/actionpack/lib/action_controller/http_authentication.rb +++ b/actionpack/lib/action_controller/http_authentication.rb @@ -68,8 +68,11 @@ module ActionController # # Simple Digest example: # + # require 'digest/md5' # class PostsController < ApplicationController - # USERS = {"dhh" => "secret"} + # REALM = "SuperSecret" + # USERS = {"dhh" => "secret", #plain text password + # "dap" => Digest:MD5::hexdigest(["dap",REALM,"secret"].join(":")) #ha1 digest password # # before_filter :authenticate, :except => [:index] # @@ -83,14 +86,18 @@ module ActionController # # private # def authenticate - # authenticate_or_request_with_http_digest(realm) do |username| + # authenticate_or_request_with_http_digest(REALM) do |username| # USERS[username] # end # end # end # - # NOTE: The +authenticate_or_request_with_http_digest+ block must return the user's password so the framework can appropriately - # hash it to check the user's credentials. Returning +nil+ will cause authentication to fail. + # NOTE: The +authenticate_or_request_with_http_digest+ block must return the user's password or the ha1 digest hash so the framework can appropriately + # hash to check the user's credentials. Returning +nil+ will cause authentication to fail. + # Storing the ha1 hash: MD5(username:realm:password), is better than storing a plain password. If + # the password file or database is compromised, the attacker would be able to use the ha1 hash to + # authenticate as the user at this +realm+, but would not have the user's password to try using at + # other sites. # # On shared hosts, Apache sometimes doesn't pass authentication headers to # FCGI instances. If your environment matches this description and you cannot @@ -177,26 +184,37 @@ module ActionController end # Raises error unless the request credentials response value matches the expected value. + # First try the password as a ha1 digest password. If this fails, then try it as a plain + # text password. def validate_digest_response(request, realm, &password_procedure) credentials = decode_credentials_header(request) valid_nonce = validate_nonce(request, credentials[:nonce]) - if valid_nonce && realm == credentials[:realm] && opaque(request.session.session_id) == credentials[:opaque] + if valid_nonce && realm == credentials[:realm] && opaque == credentials[:opaque] password = password_procedure.call(credentials[:username]) - expected = expected_response(request.env['REQUEST_METHOD'], credentials[:uri], credentials, password) - expected == credentials[:response] + + [true, false].any? do |password_is_ha1| + expected = expected_response(request.env['REQUEST_METHOD'], request.env['REQUEST_URI'], credentials, password, password_is_ha1) + expected == credentials[:response] + end end end # Returns the expected response for a request of +http_method+ to +uri+ with the decoded +credentials+ and the expected +password+ - def expected_response(http_method, uri, credentials, password) - ha1 = ::Digest::MD5.hexdigest([credentials[:username], credentials[:realm], password].join(':')) + # Optional parameter +password_is_ha1+ is set to +true+ by default, since best practice is to store ha1 digest instead + # of a plain-text password. + def expected_response(http_method, uri, credentials, password, password_is_ha1=true) + ha1 = password_is_ha1 ? password : ha1(credentials, password) ha2 = ::Digest::MD5.hexdigest([http_method.to_s.upcase, uri].join(':')) ::Digest::MD5.hexdigest([ha1, credentials[:nonce], credentials[:nc], credentials[:cnonce], credentials[:qop], ha2].join(':')) end - def encode_credentials(http_method, credentials, password) - credentials[:response] = expected_response(http_method, credentials[:uri], credentials, password) + def ha1(credentials, password) + ::Digest::MD5.hexdigest([credentials[:username], credentials[:realm], password].join(':')) + end + + def encode_credentials(http_method, credentials, password, password_is_ha1) + credentials[:response] = expected_response(http_method, credentials[:uri], credentials, password, password_is_ha1) "Digest " + credentials.sort_by {|x| x[0].to_s }.inject([]) {|a, v| a << "#{v[0]}='#{v[1]}'" }.join(', ') end @@ -213,8 +231,7 @@ module ActionController end def authentication_header(controller, realm) - session_id = controller.request.session.session_id - controller.headers["WWW-Authenticate"] = %(Digest realm="#{realm}", qop="auth", algorithm=MD5, nonce="#{nonce(session_id)}", opaque="#{opaque(session_id)}") + controller.headers["WWW-Authenticate"] = %(Digest realm="#{realm}", qop="auth", algorithm=MD5, nonce="#{nonce}", opaque="#{opaque}") end def authentication_request(controller, realm, message = nil) @@ -252,23 +269,36 @@ module ActionController # POST or PUT requests and a time-stamp for GET requests. For more details on the issues involved see Section 4 # of this document. # - # The nonce is opaque to the client. - def nonce(session_id, time = Time.now) + # The nonce is opaque to the client. Composed of Time, and hash of Time with secret + # key from the Rails session secret generated upon creation of project. Ensures + # the time cannot be modifed by client. + def nonce(time = Time.now) t = time.to_i - hashed = [t, session_id] + hashed = [t, secret_key] digest = ::Digest::MD5.hexdigest(hashed.join(":")) Base64.encode64("#{t}:#{digest}").gsub("\n", '') end - def validate_nonce(request, value) + # Might want a shorter timeout depending on whether the request + # is a PUT or POST, and if client is browser or web service. + # Can be much shorter if the Stale directive is implemented. This would + # allow a user to use new nonce without prompting user again for their + # username and password. + def validate_nonce(request, value, seconds_to_timeout=5*60) t = Base64.decode64(value).split(":").first.to_i - nonce(request.session.session_id, t) == value && (t - Time.now.to_i).abs <= 10 * 60 + nonce(t) == value && (t - Time.now.to_i).abs <= seconds_to_timeout end - # Opaque based on digest of session_id - def opaque(session_id) - Base64.encode64(::Digest::MD5::hexdigest(session_id)).gsub("\n", '') + # Opaque based on random generation - but changing each request? + def opaque() + ::Digest::MD5.hexdigest(secret_key) end + + # Set in /initializers/session_store.rb, and loaded even if sessions are not in use. + def secret_key + ActionController::Base.session_options[:secret] + end + end end end -- cgit v1.2.3 From d771e7d17f4a2c175676f7c8354aa5b161b63c2e Mon Sep 17 00:00:00 2001 From: Mike Gunderloy Date: Wed, 11 Mar 2009 08:08:09 -0500 Subject: Handle irregular plurals in polymorphic_urls [#2212 state:resolved] Signed-off-by: Pratik Naik --- actionpack/lib/action_controller/polymorphic_routes.rb | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/polymorphic_routes.rb b/actionpack/lib/action_controller/polymorphic_routes.rb index 924d1aa6bd..d9b614c237 100644 --- a/actionpack/lib/action_controller/polymorphic_routes.rb +++ b/actionpack/lib/action_controller/polymorphic_routes.rb @@ -163,7 +163,8 @@ module ActionController if parent.is_a?(Symbol) || parent.is_a?(String) string << "#{parent}_" else - string << "#{RecordIdentifier.__send__("singular_class_name", parent)}_" + string << "#{RecordIdentifier.__send__("plural_class_name", parent)}".singularize + string << "_" end end end @@ -171,7 +172,9 @@ module ActionController if record.is_a?(Symbol) || record.is_a?(String) route << "#{record}_" else - route << "#{RecordIdentifier.__send__("#{inflection}_class_name", record)}_" + route << "#{RecordIdentifier.__send__("plural_class_name", record)}" + route = route.singularize if inflection == :singular + route << "_" end action_prefix(options) + namespace + route + routing_type(options).to_s -- cgit v1.2.3 From c8c2b3820e662a2f9dfbfdae7211625adfabf15f Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Thu, 12 Mar 2009 12:22:52 -0700 Subject: Eliminate internal render stack since we only need its head and tail --- actionpack/lib/action_view/base.rb | 18 ++++++++++++++++-- actionpack/lib/action_view/renderable.rb | 26 +++++++++++--------------- 2 files changed, 27 insertions(+), 17 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index fe6053e574..0f396817a5 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -221,10 +221,12 @@ module ActionView #:nodoc: def initialize(view_paths = [], assigns_for_first_render = {}, controller = nil)#:nodoc: @assigns = assigns_for_first_render @assigns_added = nil - @_render_stack = [] @controller = controller @helpers = ProxyModule.new(self) self.view_paths = view_paths + + @_first_template = nil + @_current_template = nil end attr_reader :view_paths @@ -286,7 +288,19 @@ module ActionView #:nodoc: # Access the current template being rendered. # Returns a ActionView::Template object. def template - @_render_stack.last + @_current_template + end + + def template=(template) #:nodoc: + @_first_template ||= template + @_current_template = template + end + + def with_template(current_template) + last_template, self.template = template, current_template + yield + ensure + self.template = last_template end private diff --git a/actionpack/lib/action_view/renderable.rb b/actionpack/lib/action_view/renderable.rb index 41080ed629..ff7bc7d9de 100644 --- a/actionpack/lib/action_view/renderable.rb +++ b/actionpack/lib/action_view/renderable.rb @@ -27,23 +27,19 @@ module ActionView def render(view, local_assigns = {}) compile(local_assigns) - stack = view.instance_variable_get(:@_render_stack) - stack.push(self) - - view.send(:_evaluate_assigns_and_ivars) - view.send(:_set_controller_content_type, mime_type) if respond_to?(:mime_type) - - result = view.send(method_name(local_assigns), local_assigns) do |*names| - ivar = :@_proc_for_layout - if !view.instance_variable_defined?(:"@content_for_#{names.first}") && view.instance_variable_defined?(ivar) && (proc = view.instance_variable_get(ivar)) - view.capture(*names, &proc) - elsif view.instance_variable_defined?(ivar = :"@content_for_#{names.first || :layout}") - view.instance_variable_get(ivar) + view.with_template self do + view.send(:_evaluate_assigns_and_ivars) + view.send(:_set_controller_content_type, mime_type) if respond_to?(:mime_type) + + view.send(method_name(local_assigns), local_assigns) do |*names| + ivar = :@_proc_for_layout + if !view.instance_variable_defined?(:"@content_for_#{names.first}") && view.instance_variable_defined?(ivar) && (proc = view.instance_variable_get(ivar)) + view.capture(*names, &proc) + elsif view.instance_variable_defined?(ivar = :"@content_for_#{names.first || :layout}") + view.instance_variable_get(ivar) + end end end - - stack.pop - result end def method_name(local_assigns) -- cgit v1.2.3 From 82c6597dc244715c40151c7eb10f2016ed5ebb47 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Thu, 12 Mar 2009 12:22:52 -0700 Subject: Eliminate internal render stack since we only need its head and tail --- actionpack/lib/action_view/base.rb | 18 ++++++++++++++++-- actionpack/lib/action_view/renderable.rb | 26 +++++++++++--------------- 2 files changed, 27 insertions(+), 17 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index fe6053e574..0f396817a5 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -221,10 +221,12 @@ module ActionView #:nodoc: def initialize(view_paths = [], assigns_for_first_render = {}, controller = nil)#:nodoc: @assigns = assigns_for_first_render @assigns_added = nil - @_render_stack = [] @controller = controller @helpers = ProxyModule.new(self) self.view_paths = view_paths + + @_first_template = nil + @_current_template = nil end attr_reader :view_paths @@ -286,7 +288,19 @@ module ActionView #:nodoc: # Access the current template being rendered. # Returns a ActionView::Template object. def template - @_render_stack.last + @_current_template + end + + def template=(template) #:nodoc: + @_first_template ||= template + @_current_template = template + end + + def with_template(current_template) + last_template, self.template = template, current_template + yield + ensure + self.template = last_template end private diff --git a/actionpack/lib/action_view/renderable.rb b/actionpack/lib/action_view/renderable.rb index 41080ed629..ff7bc7d9de 100644 --- a/actionpack/lib/action_view/renderable.rb +++ b/actionpack/lib/action_view/renderable.rb @@ -27,23 +27,19 @@ module ActionView def render(view, local_assigns = {}) compile(local_assigns) - stack = view.instance_variable_get(:@_render_stack) - stack.push(self) - - view.send(:_evaluate_assigns_and_ivars) - view.send(:_set_controller_content_type, mime_type) if respond_to?(:mime_type) - - result = view.send(method_name(local_assigns), local_assigns) do |*names| - ivar = :@_proc_for_layout - if !view.instance_variable_defined?(:"@content_for_#{names.first}") && view.instance_variable_defined?(ivar) && (proc = view.instance_variable_get(ivar)) - view.capture(*names, &proc) - elsif view.instance_variable_defined?(ivar = :"@content_for_#{names.first || :layout}") - view.instance_variable_get(ivar) + view.with_template self do + view.send(:_evaluate_assigns_and_ivars) + view.send(:_set_controller_content_type, mime_type) if respond_to?(:mime_type) + + view.send(method_name(local_assigns), local_assigns) do |*names| + ivar = :@_proc_for_layout + if !view.instance_variable_defined?(:"@content_for_#{names.first}") && view.instance_variable_defined?(ivar) && (proc = view.instance_variable_get(ivar)) + view.capture(*names, &proc) + elsif view.instance_variable_defined?(ivar = :"@content_for_#{names.first || :layout}") + view.instance_variable_get(ivar) + end end end - - stack.pop - result end def method_name(local_assigns) -- cgit v1.2.3 From 5f1d6465b47333db730a4bb4ac3d2a083b7c8f3c Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Thu, 12 Mar 2009 13:32:52 -0700 Subject: Change naming to match 2.2 so life is easier on plugin developers --- actionpack/lib/action_view/base.rb | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index 0f396817a5..e19acc5c29 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -225,8 +225,8 @@ module ActionView #:nodoc: @helpers = ProxyModule.new(self) self.view_paths = view_paths - @_first_template = nil - @_current_template = nil + @_first_render = nil + @_current_render = nil end attr_reader :view_paths @@ -288,12 +288,12 @@ module ActionView #:nodoc: # Access the current template being rendered. # Returns a ActionView::Template object. def template - @_current_template + @_current_render end def template=(template) #:nodoc: - @_first_template ||= template - @_current_template = template + @_first_render ||= template + @_current_render = template end def with_template(current_template) -- cgit v1.2.3 From 91d274059536f09dffd87141e570c3eab9ebd9b4 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Thu, 12 Mar 2009 21:47:34 -0700 Subject: Return body parts directly to Rack rather than building a response string ourselves. Allows Rack middleware to orchestrate response building. --- actionpack/lib/action_controller/base.rb | 12 ++++---- actionpack/lib/action_controller/integration.rb | 10 ++++--- actionpack/lib/action_controller/response.rb | 37 +++++++++++++++++------- actionpack/lib/action_controller/test_process.rb | 4 +-- 4 files changed, 40 insertions(+), 23 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 0facf7066d..c6dd99e959 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -984,6 +984,7 @@ module ActionController #:nodoc: # of sending it as the response body to the browser. def render_to_string(options = nil, &block) #:doc: render(options, &block) + response.body ensure response.content_type = nil erase_render_results @@ -1020,7 +1021,7 @@ module ActionController #:nodoc: # Clears the rendered results, allowing for another render to be performed. def erase_render_results #:nodoc: - response.body = nil + response.body = [] @performed_render = false end @@ -1247,13 +1248,12 @@ module ActionController #:nodoc: response.status = interpret_status(status || DEFAULT_RENDER_STATUS_CODE) if append_response - response.body ||= '' - response.body << text.to_s + response.body_parts << text.to_s else response.body = case text - when Proc then text - when nil then " " # Safari doesn't pass the headers of the return if the response is zero length - else text.to_s + when Proc then text + when nil then [" "] # Safari doesn't pass the headers of the return if the response is zero length + else [text.to_s] end end end diff --git a/actionpack/lib/action_controller/integration.rb b/actionpack/lib/action_controller/integration.rb index 1c05ab0bf6..4faa263e2d 100644 --- a/actionpack/lib/action_controller/integration.rb +++ b/actionpack/lib/action_controller/integration.rb @@ -332,11 +332,13 @@ module ActionController @cookies[name] = value end - @body = "" if body.is_a?(String) - @body << body + @body_parts = [body] + @body = body else - body.each { |part| @body << part } + @body_parts = [] + body.each { |part| @body_parts << part.to_s } + @body = @body_parts.join end if @controller = ActionController::Base.last_instantiation @@ -349,7 +351,7 @@ module ActionController @response = Response.new @response.status = status.to_s @response.headers.replace(@headers) - @response.body = @body + @response.body = @body_parts end # Decorate the response with the standard behavior of the diff --git a/actionpack/lib/action_controller/response.rb b/actionpack/lib/action_controller/response.rb index ccff473df0..c69223dd69 100644 --- a/actionpack/lib/action_controller/response.rb +++ b/actionpack/lib/action_controller/response.rb @@ -40,14 +40,28 @@ module ActionController # :nodoc: delegate :default_charset, :to => 'ActionController::Base' def initialize - @status = 200 + super @header = Rack::Utils::HeaderHash.new(DEFAULT_HEADERS) + @session, @assigns = [], [] + end - @writer = lambda { |x| @body << x } - @block = nil + def body + str = '' + each { |part| str << part.to_s } + str + end - @body = "", - @session, @assigns = [], [] + def body=(body) + @body = + if body.is_a?(String) + [body] + else + body + end + end + + def body_parts + @body end def location; headers['Location'] end @@ -152,7 +166,7 @@ module ActionController # :nodoc: @writer = lambda { |x| callback.call(x) } @body.call(self, self) elsif @body.is_a?(String) - @body.each_line(&callback) + callback.call(@body) else @body.each(&callback) end @@ -162,7 +176,8 @@ module ActionController # :nodoc: end def write(str) - @writer.call str.to_s + str = str.to_s + @writer.call str str end @@ -186,7 +201,7 @@ module ActionController # :nodoc: if request && request.etag_matches?(etag) self.status = '304 Not Modified' - self.body = '' + self.body = [] end set_conditional_cache_control! @@ -195,7 +210,7 @@ module ActionController # :nodoc: def nonempty_ok_response? ok = !status || status.to_s[0..2] == '200' - ok && body.is_a?(String) && !body.empty? + ok && !body_parts.respond_to?(:call) && body_parts.any? end def set_conditional_cache_control! @@ -216,8 +231,8 @@ module ActionController # :nodoc: headers.delete('Content-Length') elsif length = headers['Content-Length'] headers['Content-Length'] = length.to_s - elsif !body.respond_to?(:call) && (!status || status.to_s[0..2] != '304') - headers["Content-Length"] = (body.respond_to?(:bytesize) ? body.bytesize : body.size).to_s + elsif !body_parts.respond_to?(:call) && (!status || status.to_s[0..2] != '304') + headers["Content-Length"] = Rack::Utils.bytesize(body).to_s end end diff --git a/actionpack/lib/action_controller/test_process.rb b/actionpack/lib/action_controller/test_process.rb index dbaec00bee..9dd09c30b4 100644 --- a/actionpack/lib/action_controller/test_process.rb +++ b/actionpack/lib/action_controller/test_process.rb @@ -258,11 +258,11 @@ module ActionController #:nodoc: # Returns binary content (downloadable file), converted to a String def binary_content - raise "Response body is not a Proc: #{body.inspect}" unless body.kind_of?(Proc) + raise "Response body is not a Proc: #{body_parts.inspect}" unless body_parts.kind_of?(Proc) require 'stringio' sio = StringIO.new - body.call(self, sio) + body_parts.call(self, sio) sio.rewind sio.read -- cgit v1.2.3 From 3d260760f035c5aab11ab218881ed36e3046157b Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 00:25:05 -0700 Subject: Introduce flush_output_buffer to append the buffer to the response body then start a new buffer. Useful for pushing custom parts to the response body without disrupting template rendering. --- actionpack/lib/action_view/helpers/capture_helper.rb | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/capture_helper.rb b/actionpack/lib/action_view/helpers/capture_helper.rb index e86ca27f31..9e39536653 100644 --- a/actionpack/lib/action_view/helpers/capture_helper.rb +++ b/actionpack/lib/action_view/helpers/capture_helper.rb @@ -131,6 +131,14 @@ module ActionView ensure self.output_buffer = old_buffer end + + # Add the output buffer to the response body and start a new one. + def flush_output_buffer #:nodoc: + if output_buffer && output_buffer != '' + response.body_parts << output_buffer + self.output_buffer = '' + end + end end end end -- cgit v1.2.3 From 79b0b1a0ef926e91388e24bc77d3831f6d50b13d Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 02:15:51 -0700 Subject: Extract Response#string_body? --- actionpack/lib/action_controller/response.rb | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/response.rb b/actionpack/lib/action_controller/response.rb index c69223dd69..febe4ccf29 100644 --- a/actionpack/lib/action_controller/response.rb +++ b/actionpack/lib/action_controller/response.rb @@ -210,7 +210,11 @@ module ActionController # :nodoc: def nonempty_ok_response? ok = !status || status.to_s[0..2] == '200' - ok && !body_parts.respond_to?(:call) && body_parts.any? + ok && string_body? + end + + def string_body? + !body_parts.respond_to?(:call) && body_parts.any? && body_parts.all? { |part| part.is_a?(String) } end def set_conditional_cache_control! @@ -231,7 +235,7 @@ module ActionController # :nodoc: headers.delete('Content-Length') elsif length = headers['Content-Length'] headers['Content-Length'] = length.to_s - elsif !body_parts.respond_to?(:call) && (!status || status.to_s[0..2] != '304') + elsif string_body? && (!status || status.to_s[0..2] != '304') headers["Content-Length"] = Rack::Utils.bytesize(body).to_s end end -- cgit v1.2.3 From 7c1714cbd0b37d1fc5ca2ac3e08980943454d516 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 02:36:00 -0700 Subject: Body parts: future rendering, threaded future, queued future, open-uri example --- actionpack/lib/action_view/base.rb | 10 +++++++-- actionpack/lib/action_view/body_parts/future.rb | 26 +++++++++++++++++++++++ actionpack/lib/action_view/body_parts/open_uri.rb | 13 ++++++++++++ actionpack/lib/action_view/body_parts/queued.rb | 21 ++++++++++++++++++ actionpack/lib/action_view/body_parts/threaded.rb | 21 ++++++++++++++++++ 5 files changed, 89 insertions(+), 2 deletions(-) create mode 100644 actionpack/lib/action_view/body_parts/future.rb create mode 100644 actionpack/lib/action_view/body_parts/open_uri.rb create mode 100644 actionpack/lib/action_view/body_parts/queued.rb create mode 100644 actionpack/lib/action_view/body_parts/threaded.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index e19acc5c29..3bbd2ca530 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -288,12 +288,12 @@ module ActionView #:nodoc: # Access the current template being rendered. # Returns a ActionView::Template object. def template - @_current_render + Thread.current[:_current_render] end def template=(template) #:nodoc: @_first_render ||= template - @_current_render = template + Thread.current[:_current_render] = template end def with_template(current_template) @@ -303,6 +303,12 @@ module ActionView #:nodoc: self.template = last_template end + def punctuate_body!(part) + flush_output_buffer + response.body_parts << part + nil + end + private # Evaluates the local assigns and controller ivars, pushes them to the view. def _evaluate_assigns_and_ivars #:nodoc: diff --git a/actionpack/lib/action_view/body_parts/future.rb b/actionpack/lib/action_view/body_parts/future.rb new file mode 100644 index 0000000000..a5291c6e8c --- /dev/null +++ b/actionpack/lib/action_view/body_parts/future.rb @@ -0,0 +1,26 @@ +module ActionView + module BodyParts + class Future + def initialize(&block) + @block = block + @parts = [] + end + + def to_s + finish + body + end + + protected + def work + @block.call(@parts) + end + + def body + str = '' + @parts.each { |part| str << part.to_s } + str + end + end + end +end diff --git a/actionpack/lib/action_view/body_parts/open_uri.rb b/actionpack/lib/action_view/body_parts/open_uri.rb new file mode 100644 index 0000000000..8ebd17b4a1 --- /dev/null +++ b/actionpack/lib/action_view/body_parts/open_uri.rb @@ -0,0 +1,13 @@ +require 'action_view/body_parts/threaded' +require 'open-uri' + +module ActionView + module BodyParts + class OpenUri < Threaded + def initialize(url) + url = URI::Generic === url ? url : URI.parse(url) + super(true) { |parts| parts << url.read } + end + end + end +end diff --git a/actionpack/lib/action_view/body_parts/queued.rb b/actionpack/lib/action_view/body_parts/queued.rb new file mode 100644 index 0000000000..f8501f6a85 --- /dev/null +++ b/actionpack/lib/action_view/body_parts/queued.rb @@ -0,0 +1,21 @@ +require 'action_view/body_parts/future' + +module ActionView + module BodyParts + class Queued < Future + def initialize(job, &block) + super(&block) + enqueue(job) + end + + protected + def enqueue(job) + @receipt = submit(job) + end + + def finish + @parts << redeem(@receipt) + end + end + end +end diff --git a/actionpack/lib/action_view/body_parts/threaded.rb b/actionpack/lib/action_view/body_parts/threaded.rb new file mode 100644 index 0000000000..34800bf9c7 --- /dev/null +++ b/actionpack/lib/action_view/body_parts/threaded.rb @@ -0,0 +1,21 @@ +require 'action_view/body_parts/future' + +module ActionView + module BodyParts + class Threaded < Future + def initialize(concurrent = false, &block) + super(&block) + concurrent ? start : work + end + + protected + def start + @worker = Thread.new { work } + end + + def finish + @worker.join if @worker && @worker.alive? + end + end + end +end -- cgit v1.2.3 From 5d76dee329282acc918de50fecde869f1431e2f1 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 02:55:24 -0700 Subject: Example using an edge side include body part to fetch queued rendering results --- actionpack/lib/action_view/body_parts/open_uri.rb | 13 ------------- 1 file changed, 13 deletions(-) delete mode 100644 actionpack/lib/action_view/body_parts/open_uri.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/body_parts/open_uri.rb b/actionpack/lib/action_view/body_parts/open_uri.rb deleted file mode 100644 index 8ebd17b4a1..0000000000 --- a/actionpack/lib/action_view/body_parts/open_uri.rb +++ /dev/null @@ -1,13 +0,0 @@ -require 'action_view/body_parts/threaded' -require 'open-uri' - -module ActionView - module BodyParts - class OpenUri < Threaded - def initialize(url) - url = URI::Generic === url ? url : URI.parse(url) - super(true) { |parts| parts << url.read } - end - end - end -end -- cgit v1.2.3 From b2f98c13a3308e6db618d6f3f9f706cbc19f13fd Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 03:16:14 -0700 Subject: Simplify parts and tests --- actionpack/lib/action_view/body_parts/future.rb | 16 ---------------- actionpack/lib/action_view/body_parts/queued.rb | 13 +++++-------- actionpack/lib/action_view/body_parts/threaded.rb | 13 ++++++++++++- 3 files changed, 17 insertions(+), 25 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/body_parts/future.rb b/actionpack/lib/action_view/body_parts/future.rb index a5291c6e8c..f03c2b395b 100644 --- a/actionpack/lib/action_view/body_parts/future.rb +++ b/actionpack/lib/action_view/body_parts/future.rb @@ -1,26 +1,10 @@ module ActionView module BodyParts class Future - def initialize(&block) - @block = block - @parts = [] - end - def to_s finish body end - - protected - def work - @block.call(@parts) - end - - def body - str = '' - @parts.each { |part| str << part.to_s } - str - end end end end diff --git a/actionpack/lib/action_view/body_parts/queued.rb b/actionpack/lib/action_view/body_parts/queued.rb index f8501f6a85..618999742b 100644 --- a/actionpack/lib/action_view/body_parts/queued.rb +++ b/actionpack/lib/action_view/body_parts/queued.rb @@ -3,18 +3,15 @@ require 'action_view/body_parts/future' module ActionView module BodyParts class Queued < Future - def initialize(job, &block) - super(&block) - enqueue(job) + attr_reader :body + + def initialize(job) + @receipt = enqueue(job) end protected - def enqueue(job) - @receipt = submit(job) - end - def finish - @parts << redeem(@receipt) + @body = redeem(@receipt) end end end diff --git a/actionpack/lib/action_view/body_parts/threaded.rb b/actionpack/lib/action_view/body_parts/threaded.rb index 34800bf9c7..a2347a2f0e 100644 --- a/actionpack/lib/action_view/body_parts/threaded.rb +++ b/actionpack/lib/action_view/body_parts/threaded.rb @@ -4,11 +4,22 @@ module ActionView module BodyParts class Threaded < Future def initialize(concurrent = false, &block) - super(&block) + @block = block + @parts = [] concurrent ? start : work end protected + def work + @block.call(@parts) + end + + def body + str = '' + @parts.each { |part| str << part.to_s } + str + end + def start @worker = Thread.new { work } end -- cgit v1.2.3 From eced3d8c55c1bbae6915d7c6523c341bc682509a Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Fri, 13 Mar 2009 17:13:10 -0500 Subject: Update rack to fix multipart uploads with an empty file [#1945 state:resolved] --- .../lib/action_controller/vendor/rack-1.0/rack.rb | 1 + .../vendor/rack-1.0/rack/chunked.rb | 49 ++++++++++++++++++++ .../action_controller/vendor/rack-1.0/rack/file.rb | 2 +- .../vendor/rack-1.0/rack/handler/cgi.rb | 4 ++ .../vendor/rack-1.0/rack/handler/fastcgi.rb | 3 ++ .../vendor/rack-1.0/rack/handler/lsws.rb | 5 +- .../vendor/rack-1.0/rack/handler/mongrel.rb | 4 +- .../vendor/rack-1.0/rack/handler/scgi.rb | 4 +- .../vendor/rack-1.0/rack/handler/thin.rb | 3 ++ .../vendor/rack-1.0/rack/handler/webrick.rb | 3 +- .../action_controller/vendor/rack-1.0/rack/lint.rb | 54 ++++++++-------------- .../vendor/rack-1.0/rack/urlmap.rb | 6 ++- .../vendor/rack-1.0/rack/utils.rb | 2 +- 13 files changed, 98 insertions(+), 42 deletions(-) create mode 100644 actionpack/lib/action_controller/vendor/rack-1.0/rack/chunked.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb index e3e20ed2a3..7fab1a7931 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb @@ -28,6 +28,7 @@ module Rack autoload :Builder, "rack/builder" autoload :Cascade, "rack/cascade" + autoload :Chunked, "rack/chunked" autoload :CommonLogger, "rack/commonlogger" autoload :ConditionalGet, "rack/conditionalget" autoload :ContentLength, "rack/content_length" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/chunked.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/chunked.rb new file mode 100644 index 0000000000..280d89dd65 --- /dev/null +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/chunked.rb @@ -0,0 +1,49 @@ +require 'rack/utils' + +module Rack + + # Middleware that applies chunked transfer encoding to response bodies + # when the response does not include a Content-Length header. + class Chunked + include Rack::Utils + + def initialize(app) + @app = app + end + + def call(env) + status, headers, body = @app.call(env) + headers = HeaderHash.new(headers) + + if env['HTTP_VERSION'] == 'HTTP/1.0' || + STATUS_WITH_NO_ENTITY_BODY.include?(status) || + headers['Content-Length'] || + headers['Transfer-Encoding'] + [status, headers.to_hash, body] + else + dup.chunk(status, headers, body) + end + end + + def chunk(status, headers, body) + @body = body + headers.delete('Content-Length') + headers['Transfer-Encoding'] = 'chunked' + [status, headers.to_hash, self] + end + + def each + term = "\r\n" + @body.each do |chunk| + size = bytesize(chunk) + next if size == 0 + yield [size.to_s(16), term, chunk, term].join + end + yield ["0", term, "", term].join + end + + def close + @body.close if @body.respond_to?(:close) + end + end +end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/file.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/file.rb index 7869227a36..fe62bd6b86 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/file.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/file.rb @@ -60,7 +60,7 @@ module Rack body = self else body = [F.read(@path)] - size = body.first.size + size = Utils.bytesize(body.first) end [200, { diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/cgi.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/cgi.rb index f2c976cf46..e38156c7f0 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/cgi.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/cgi.rb @@ -1,3 +1,5 @@ +require 'rack/content_length' + module Rack module Handler class CGI @@ -6,6 +8,8 @@ module Rack end def self.serve(app) + app = ContentLength.new(app) + env = ENV.to_hash env.delete "HTTP_CONTENT_LENGTH" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/fastcgi.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/fastcgi.rb index f03e1615c9..6324c7d274 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/fastcgi.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/fastcgi.rb @@ -1,5 +1,6 @@ require 'fcgi' require 'socket' +require 'rack/content_length' module Rack module Handler @@ -29,6 +30,8 @@ module Rack end def self.serve(request, app) + app = Rack::ContentLength.new(app) + env = request.env env.delete "HTTP_CONTENT_LENGTH" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb index dfc79c204b..c65ba3ec8e 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/lsws.rb @@ -1,5 +1,6 @@ require 'lsapi' -#require 'cgi' +require 'rack/content_length' + module Rack module Handler class LSWS @@ -9,6 +10,8 @@ module Rack end end def self.serve(app) + app = Rack::ContentLength.new(app) + env = ENV.to_hash env.delete "HTTP_CONTENT_LENGTH" env["SCRIPT_NAME"] = "" if env["SCRIPT_NAME"] == "/" diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/mongrel.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/mongrel.rb index 178a1a8fe4..f0c0d58330 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/mongrel.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/mongrel.rb @@ -1,5 +1,7 @@ require 'mongrel' require 'stringio' +require 'rack/content_length' +require 'rack/chunked' module Rack module Handler @@ -33,7 +35,7 @@ module Rack end def initialize(app) - @app = app + @app = Rack::Chunked.new(Rack::ContentLength.new(app)) end def process(request, response) diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/scgi.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/scgi.rb index fd18a8359b..9495c66374 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/scgi.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/scgi.rb @@ -1,5 +1,7 @@ require 'scgi' require 'stringio' +require 'rack/content_length' +require 'rack/chunked' module Rack module Handler @@ -14,7 +16,7 @@ module Rack end def initialize(settings = {}) - @app = settings[:app] + @app = Rack::Chunked.new(Rack::ContentLength.new(settings[:app])) @log = Object.new def @log.info(*args); end def @log.error(*args); end diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/thin.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/thin.rb index 7ad088b36a..3d4fedff75 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/thin.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/thin.rb @@ -1,9 +1,12 @@ require "thin" +require "rack/content_length" +require "rack/chunked" module Rack module Handler class Thin def self.run(app, options={}) + app = Rack::Chunked.new(Rack::ContentLength.new(app)) server = ::Thin::Server.new(options[:Host] || '0.0.0.0', options[:Port] || 8080, app) diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb index 138aae0ee9..829e7d6bf8 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/handler/webrick.rb @@ -1,5 +1,6 @@ require 'webrick' require 'stringio' +require 'rack/content_length' module Rack module Handler @@ -14,7 +15,7 @@ module Rack def initialize(server, app) super server - @app = app + @app = Rack::ContentLength.new(app) end def service(req, res) diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb index ec4dac96f8..44a33ce36e 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/lint.rb @@ -374,59 +374,43 @@ module Rack ## === The Content-Length def check_content_length(status, headers, env) - chunked_response = false - headers.each { |key, value| - if key.downcase == 'transfer-encoding' - chunked_response = value.downcase != 'identity' - end - } - headers.each { |key, value| if key.downcase == 'content-length' - ## There must be a Content-Length, except when the - ## +Status+ is 1xx, 204 or 304, in which case there must be none - ## given. + ## There must not be a Content-Length header when the + ## +Status+ is 1xx, 204 or 304. assert("Content-Length header found in #{status} response, not allowed") { not Rack::Utils::STATUS_WITH_NO_ENTITY_BODY.include? status.to_i } - assert('Content-Length header should not be used if body is chunked') { - not chunked_response - } - bytes = 0 string_body = true - @body.each { |part| - unless part.kind_of?(String) - string_body = false - break - end + if @body.respond_to?(:to_ary) + @body.each { |part| + unless part.kind_of?(String) + string_body = false + break + end - bytes += Rack::Utils.bytesize(part) - } - - if env["REQUEST_METHOD"] == "HEAD" - assert("Response body was given for HEAD request, but should be empty") { - bytes == 0 + bytes += Rack::Utils.bytesize(part) } - else - if string_body - assert("Content-Length header was #{value}, but should be #{bytes}") { - value == bytes.to_s + + if env["REQUEST_METHOD"] == "HEAD" + assert("Response body was given for HEAD request, but should be empty") { + bytes == 0 } + else + if string_body + assert("Content-Length header was #{value}, but should be #{bytes}") { + value == bytes.to_s + } + end end end return end } - - if [ String, Array ].include?(@body.class) && !chunked_response - assert('No Content-Length header found') { - Rack::Utils::STATUS_WITH_NO_ENTITY_BODY.include? status.to_i - } - end end ## === The Body diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/urlmap.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/urlmap.rb index eb1457a850..0ff32df181 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/urlmap.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/urlmap.rb @@ -12,7 +12,11 @@ module Rack # first, since they are most specific. class URLMap - def initialize(map) + def initialize(map = {}) + remap(map) + end + + def remap(map) @mapping = map.map { |location, app| if location =~ %r{\Ahttps?://(.*?)(/.*)} host, location = $1, $2 diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb index e86d4ccdcd..0a61bce707 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack/utils.rb @@ -372,7 +372,7 @@ module Rack data = body end - Utils.normalize_params(params, name, data) + Utils.normalize_params(params, name, data) unless data.nil? break if buf.empty? || content_length == -1 } -- cgit v1.2.3 From 5b025a1d119eaf09f5376209da212b76725747f8 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Fri, 13 Mar 2009 17:13:18 -0500 Subject: Revert 5b7527ca "Failing test for routes with member & requirement" [#2054 state:wontfix] --- actionpack/lib/action_controller/resources.rb | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/resources.rb b/actionpack/lib/action_controller/resources.rb index 0a89c4b3d5..5f71a105c8 100644 --- a/actionpack/lib/action_controller/resources.rb +++ b/actionpack/lib/action_controller/resources.rb @@ -670,12 +670,7 @@ module ActionController when "show", "edit"; default_options.merge(add_conditions_for(resource.conditions, method || :get)).merge(resource.requirements(require_id)) when "update"; default_options.merge(add_conditions_for(resource.conditions, method || :put)).merge(resource.requirements(require_id)) when "destroy"; default_options.merge(add_conditions_for(resource.conditions, method || :delete)).merge(resource.requirements(require_id)) - else - if method.nil? || resource.member_methods.nil? || resource.member_methods[method.to_sym].nil? - default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) - else - resource.member_methods[method.to_sym].include?(action) ? default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements(require_id)) : default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) - end + else default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) end end end -- cgit v1.2.3 From 4a7b11d5d857a0f5ce6eb8af7a6dfcb94f31fcfa Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Fri, 13 Mar 2009 18:49:53 -0700 Subject: Less ceremony --- .../lib/action_view/body_parts/concurrent_block.rb | 25 +++++++++++++++++ actionpack/lib/action_view/body_parts/future.rb | 10 ------- actionpack/lib/action_view/body_parts/queued.rb | 18 ------------ actionpack/lib/action_view/body_parts/threaded.rb | 32 ---------------------- 4 files changed, 25 insertions(+), 60 deletions(-) create mode 100644 actionpack/lib/action_view/body_parts/concurrent_block.rb delete mode 100644 actionpack/lib/action_view/body_parts/future.rb delete mode 100644 actionpack/lib/action_view/body_parts/queued.rb delete mode 100644 actionpack/lib/action_view/body_parts/threaded.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/body_parts/concurrent_block.rb b/actionpack/lib/action_view/body_parts/concurrent_block.rb new file mode 100644 index 0000000000..28a3a3bf4d --- /dev/null +++ b/actionpack/lib/action_view/body_parts/concurrent_block.rb @@ -0,0 +1,25 @@ +module ActionView + module BodyParts + class ConcurrentBlock + def initialize(&block) + @block = block + @body = [] + start + end + + def to_s + finish + @body.join + end + + protected + def start + @worker = Thread.new { @block.call(@body) } + end + + def finish + @worker.join if @worker && @worker.alive? + end + end + end +end diff --git a/actionpack/lib/action_view/body_parts/future.rb b/actionpack/lib/action_view/body_parts/future.rb deleted file mode 100644 index f03c2b395b..0000000000 --- a/actionpack/lib/action_view/body_parts/future.rb +++ /dev/null @@ -1,10 +0,0 @@ -module ActionView - module BodyParts - class Future - def to_s - finish - body - end - end - end -end diff --git a/actionpack/lib/action_view/body_parts/queued.rb b/actionpack/lib/action_view/body_parts/queued.rb deleted file mode 100644 index 618999742b..0000000000 --- a/actionpack/lib/action_view/body_parts/queued.rb +++ /dev/null @@ -1,18 +0,0 @@ -require 'action_view/body_parts/future' - -module ActionView - module BodyParts - class Queued < Future - attr_reader :body - - def initialize(job) - @receipt = enqueue(job) - end - - protected - def finish - @body = redeem(@receipt) - end - end - end -end diff --git a/actionpack/lib/action_view/body_parts/threaded.rb b/actionpack/lib/action_view/body_parts/threaded.rb deleted file mode 100644 index a2347a2f0e..0000000000 --- a/actionpack/lib/action_view/body_parts/threaded.rb +++ /dev/null @@ -1,32 +0,0 @@ -require 'action_view/body_parts/future' - -module ActionView - module BodyParts - class Threaded < Future - def initialize(concurrent = false, &block) - @block = block - @parts = [] - concurrent ? start : work - end - - protected - def work - @block.call(@parts) - end - - def body - str = '' - @parts.each { |part| str << part.to_s } - str - end - - def start - @worker = Thread.new { work } - end - - def finish - @worker.join if @worker && @worker.alive? - end - end - end -end -- cgit v1.2.3 From 07710fd3e0c5c84521b7929738ba33cea99bc108 Mon Sep 17 00:00:00 2001 From: Mike Gunderloy Date: Sat, 14 Mar 2009 10:06:00 -0500 Subject: Fix requirements for additional member/collection routes [#2054 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_controller/resources.rb | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/resources.rb b/actionpack/lib/action_controller/resources.rb index 5f71a105c8..86abb7b2f4 100644 --- a/actionpack/lib/action_controller/resources.rb +++ b/actionpack/lib/action_controller/resources.rb @@ -630,7 +630,7 @@ module ActionController action_path = resource.options[:path_names][action] if resource.options[:path_names].is_a?(Hash) action_path ||= Base.resources_path_names[action] || action - map_resource_routes(map, resource, action, "#{resource.member_path}#{resource.action_separator}#{action_path}", "#{action}_#{resource.shallow_name_prefix}#{resource.singular}", m) + map_resource_routes(map, resource, action, "#{resource.member_path}#{resource.action_separator}#{action_path}", "#{action}_#{resource.shallow_name_prefix}#{resource.singular}", m, { :force_id => true }) end end end @@ -641,9 +641,9 @@ module ActionController map_resource_routes(map, resource, :destroy, resource.member_path, route_path) end - def map_resource_routes(map, resource, action, route_path, route_name = nil, method = nil) + def map_resource_routes(map, resource, action, route_path, route_name = nil, method = nil, resource_options = {} ) if resource.has_action?(action) - action_options = action_options_for(action, resource, method) + action_options = action_options_for(action, resource, method, resource_options) formatted_route_path = "#{route_path}.:format" if route_name && @set.named_routes[route_name.to_sym].nil? @@ -660,9 +660,10 @@ module ActionController end end - def action_options_for(action, resource, method = nil) + def action_options_for(action, resource, method = nil, resource_options = {}) default_options = { :action => action.to_s } require_id = !resource.kind_of?(SingletonResource) + force_id = resource_options[:force_id] && !resource.kind_of?(SingletonResource) case default_options[:action] when "index", "new"; default_options.merge(add_conditions_for(resource.conditions, method || :get)).merge(resource.requirements) @@ -670,7 +671,7 @@ module ActionController when "show", "edit"; default_options.merge(add_conditions_for(resource.conditions, method || :get)).merge(resource.requirements(require_id)) when "update"; default_options.merge(add_conditions_for(resource.conditions, method || :put)).merge(resource.requirements(require_id)) when "destroy"; default_options.merge(add_conditions_for(resource.conditions, method || :delete)).merge(resource.requirements(require_id)) - else default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements) + else default_options.merge(add_conditions_for(resource.conditions, method)).merge(resource.requirements(force_id)) end end end -- cgit v1.2.3 From 112056333f6ad2492a37b7eb9d647ecd23980592 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Sat, 14 Mar 2009 10:37:20 -0500 Subject: Add Rack version to Rails info --- actionpack/lib/action_controller/vendor/rack-1.0/rack.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb index 7fab1a7931..6c73d64612 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb @@ -3,7 +3,7 @@ # Rack is freely distributable under the terms of an MIT-style license. # See COPYING or http://www.opensource.org/licenses/mit-license.php. -$:.unshift(File.expand_path(File.dirname(__FILE__))) +$: << File.expand_path(File.dirname(__FILE__)) # The Rack main module, serving as a namespace for all core Rack @@ -23,7 +23,7 @@ module Rack # Return the Rack release as a dotted string. def self.release - "0.4" + "1.0 bundled" end autoload :Builder, "rack/builder" -- cgit v1.2.3 From 7706b57034e91820cf83445aede57c54ab66ac2d Mon Sep 17 00:00:00 2001 From: misfo Date: Sat, 14 Mar 2009 10:42:02 -0500 Subject: allowed render :file to take Pathnames [#2220 state:resolved] Signed-off-by: Joshua Peek --- actionpack/lib/action_view/template.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/template.rb b/actionpack/lib/action_view/template.rb index 0dd3a7e619..c339c8a554 100644 --- a/actionpack/lib/action_view/template.rb +++ b/actionpack/lib/action_view/template.rb @@ -218,7 +218,7 @@ module ActionView #:nodoc: # Returns file split into an array # [base_path, name, locale, format, extension] def split(file) - if m = file.match(/^(.*\/)?([^\.]+)\.(.*)$/) + if m = file.to_s.match(/^(.*\/)?([^\.]+)\.(.*)$/) base_path = m[1] name = m[2] extensions = m[3] -- cgit v1.2.3 From 73fc42cc0b5e94541480032c2941a50edd4080c2 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 15 Mar 2009 22:06:50 -0500 Subject: Prepare for final 2.3 release --- actionpack/lib/action_pack/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_pack/version.rb b/actionpack/lib/action_pack/version.rb index f03a2a7605..e0aa2a5f2f 100644 --- a/actionpack/lib/action_pack/version.rb +++ b/actionpack/lib/action_pack/version.rb @@ -2,7 +2,7 @@ module ActionPack #:nodoc: module VERSION #:nodoc: MAJOR = 2 MINOR = 3 - TINY = 1 + TINY = 2 STRING = [MAJOR, MINOR, TINY].join('.') end -- cgit v1.2.3 From 39ff550fa88da9a22d8c21ca872f5e4d0d83f8d4 Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Sun, 15 Mar 2009 22:54:26 -0500 Subject: Ensure our bundled version of rack is at the front of the load path --- actionpack/lib/action_controller/vendor/rack-1.0/rack.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb index 6c73d64612..6349b95094 100644 --- a/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb +++ b/actionpack/lib/action_controller/vendor/rack-1.0/rack.rb @@ -3,7 +3,7 @@ # Rack is freely distributable under the terms of an MIT-style license. # See COPYING or http://www.opensource.org/licenses/mit-license.php. -$: << File.expand_path(File.dirname(__FILE__)) +$:.unshift(File.expand_path(File.dirname(__FILE__))) # The Rack main module, serving as a namespace for all core Rack -- cgit v1.2.3 From 46c12fdcb6fb11ae62786eeafd0d1784343b3daa Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Sun, 15 Mar 2009 23:29:00 -0500 Subject: ruby 1.9 compat: Pathname doesn't support =~ --- actionpack/lib/action_view/paths.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/paths.rb b/actionpack/lib/action_view/paths.rb index 37d96b2f82..8cc3fe291c 100644 --- a/actionpack/lib/action_view/paths.rb +++ b/actionpack/lib/action_view/paths.rb @@ -61,7 +61,7 @@ module ActionView #:nodoc: end end - return Template.new(original_template_path, original_template_path =~ /\A\// ? "" : ".") if File.file?(original_template_path) + return Template.new(original_template_path, original_template_path.to_s =~ /\A\// ? "" : ".") if File.file?(original_template_path) raise MissingTemplate.new(self, original_template_path, format) end -- cgit v1.2.3 From 18eb80ccc7e932f9a6c00462ceaeea648631b120 Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Mon, 16 Mar 2009 11:28:36 +0000 Subject: Merge docrails --- actionpack/lib/action_controller/integration.rb | 2 +- actionpack/lib/action_view/helpers/date_helper.rb | 4 ++-- actionpack/lib/action_view/helpers/number_helper.rb | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/integration.rb b/actionpack/lib/action_controller/integration.rb index 1c05ab0bf6..26b695570b 100644 --- a/actionpack/lib/action_controller/integration.rb +++ b/actionpack/lib/action_controller/integration.rb @@ -5,7 +5,7 @@ require 'active_support/test_case' module ActionController module Integration #:nodoc: # An integration Session instance represents a set of requests and responses - # performed sequentially by some virtual user. Becase you can instantiate + # performed sequentially by some virtual user. Because you can instantiate # multiple sessions and run them side-by-side, you can also mimic (to some # limited extent) multiple simultaneous users interacting with your system. # diff --git a/actionpack/lib/action_view/helpers/date_helper.rb b/actionpack/lib/action_view/helpers/date_helper.rb index b7ef1fb90d..c74909a360 100644 --- a/actionpack/lib/action_view/helpers/date_helper.rb +++ b/actionpack/lib/action_view/helpers/date_helper.rb @@ -876,8 +876,8 @@ module ActionView input_name_from_type(type).gsub(/([\[\(])|(\]\[)/, '_').gsub(/[\]\)]/, '') end - # Given an ordering of datetime components, create the selection html - # and join them with their appropriate seperators + # Given an ordering of datetime components, create the selection HTML + # and join them with their appropriate separators. def build_selects_from_types(order) select = '' order.reverse.each do |type| diff --git a/actionpack/lib/action_view/helpers/number_helper.rb b/actionpack/lib/action_view/helpers/number_helper.rb index 539f43c6e3..dea958deaf 100644 --- a/actionpack/lib/action_view/helpers/number_helper.rb +++ b/actionpack/lib/action_view/helpers/number_helper.rb @@ -140,7 +140,7 @@ module ActionView # number_with_delimiter(12345678) # => 12,345,678 # number_with_delimiter(12345678.05) # => 12,345,678.05 # number_with_delimiter(12345678, :delimiter => ".") # => 12.345.678 - # number_with_delimiter(12345678, :seperator => ",") # => 12,345,678 + # number_with_delimiter(12345678, :separator => ",") # => 12,345,678 # number_with_delimiter(98765432.98, :delimiter => " ", :separator => ",") # # => 98 765 432,98 # -- cgit v1.2.3 From d36df5e7a8a2791bb890afa0c11b8f3985293c21 Mon Sep 17 00:00:00 2001 From: Clemens Kofler Date: Tue, 17 Mar 2009 14:46:19 +0100 Subject: Hidden field with check box goes first. --- actionpack/lib/action_view/helpers/form_helper.rb | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/form_helper.rb b/actionpack/lib/action_view/helpers/form_helper.rb index a589bcba2a..93b8ae687f 100644 --- a/actionpack/lib/action_view/helpers/form_helper.rb +++ b/actionpack/lib/action_view/helpers/form_helper.rb @@ -657,17 +657,17 @@ module ActionView # ==== Examples # # Let's say that @post.validated? is 1: # check_box("post", "validated") - # # => - # # + # # => + # # # # # Let's say that @puppy.gooddog is "no": # check_box("puppy", "gooddog", {}, "yes", "no") - # # => - # # + # # => + # # # # check_box("eula", "accepted", { :class => 'eula_check' }, "yes", "no") - # # => - # # + # # => + # # # def check_box(object_name, method, options = {}, checked_value = "1", unchecked_value = "0") InstanceTag.new(object_name, method, self, options.delete(:object)).to_check_box_tag(options, checked_value, unchecked_value) -- cgit v1.2.3 From a8bf6fa30882cdbb2c84b1840f3bd3f10894af3d Mon Sep 17 00:00:00 2001 From: Xavier Noria Date: Tue, 17 Mar 2009 18:50:50 +0100 Subject: update explanation of check box generation according to f400209 --- actionpack/lib/action_view/helpers/form_helper.rb | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/form_helper.rb b/actionpack/lib/action_view/helpers/form_helper.rb index 93b8ae687f..4e1927a897 100644 --- a/actionpack/lib/action_view/helpers/form_helper.rb +++ b/actionpack/lib/action_view/helpers/form_helper.rb @@ -628,7 +628,7 @@ module ActionView # # The HTML specification says unchecked check boxes are not successful, and # thus web browsers do not send them. Unfortunately this introduces a gotcha: - # if an Invoice model has a +paid+ flag, and in the form that edits a paid + # if an +Invoice+ model has a +paid+ flag, and in the form that edits a paid # invoice the user unchecks its check box, no +paid+ parameter is sent. So, # any mass-assignment idiom like # @@ -636,12 +636,15 @@ module ActionView # # wouldn't update the flag. # - # To prevent this the helper generates a hidden field with the same name as - # the checkbox after the very check box. So, the client either sends only the - # hidden field (representing the check box is unchecked), or both fields. - # Since the HTML specification says key/value pairs have to be sent in the - # same order they appear in the form and Rails parameters extraction always - # gets the first occurrence of any given key, that works in ordinary forms. + # To prevent this the helper generates an auxiliary hidden field before + # the very check box. The hidden field has the same name and its + # attributes mimick an unchecked check box. + # + # This way, the client either sends only the hidden field (representing + # the check box is unchecked), or both fields. Since the HTML specification + # says key/value pairs have to be sent in the same order they appear in the + # form, and parameters extraction gets the last occurrence of any repeated + # key in the query string, that works for ordinary forms. # # Unfortunately that workaround does not work when the check box goes # within an array-like parameter, as in -- cgit v1.2.3 From 168e3958df38b7f6738d60f2510a2e6d1ebcc9fb Mon Sep 17 00:00:00 2001 From: Giles Bowkett Date: Tue, 17 Mar 2009 12:41:15 -0700 Subject: this page referred to an :href_options keyword hash, in fact the correct keyword (the one the code responds to) is :html --- actionpack/lib/action_view/helpers/text_helper.rb | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/text_helper.rb b/actionpack/lib/action_view/helpers/text_helper.rb index 48bf4717ad..573b99b96e 100644 --- a/actionpack/lib/action_view/helpers/text_helper.rb +++ b/actionpack/lib/action_view/helpers/text_helper.rb @@ -324,7 +324,7 @@ module ActionView # Turns all URLs and e-mail addresses into clickable links. The :link option # will limit what should be linked. You can add HTML attributes to the links using - # :href_options. Possible values for :link are :all (default), + # :html. Possible values for :link are :all (default), # :email_addresses, and :urls. If a block is given, each URL and # e-mail address is yielded and the result is used as the link text. # @@ -341,7 +341,7 @@ module ActionView # # => "Visit http://www.loudthinking.com/ or e-mail david@loudthinking.com" # # post_body = "Welcome to my new blog at http://www.myblog.com/. Please e-mail me at me@email.com." - # auto_link(post_body, :href_options => { :target => '_blank' }) do |text| + # auto_link(post_body, :html => { :target => '_blank' }) do |text| # truncate(text, 15) # end # # => "Welcome to my new blog at http://www.m.... @@ -359,7 +359,7 @@ module ActionView # auto_link(post_body, :all, :target => "_blank") # => Once upon\na time # # => "Welcome to my new blog at http://www.myblog.com. # Please e-mail me at me@email.com." - def auto_link(text, *args, &block)#link = :all, href_options = {}, &block) + def auto_link(text, *args, &block)#link = :all, html = {}, &block) return '' if text.blank? options = args.size == 2 ? {} : args.extract_options! # this is necessary because the old auto_link API has a Hash as its last parameter -- cgit v1.2.3 From e8501a15a84f4c0d894273b0decedf64cce66c76 Mon Sep 17 00:00:00 2001 From: Xavier Noria Date: Tue, 17 Mar 2009 21:01:50 +0100 Subject: clarifies a bit more what's the issue with check boxes and arrays of parameters --- actionpack/lib/action_view/helpers/form_helper.rb | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/helpers/form_helper.rb b/actionpack/lib/action_view/helpers/form_helper.rb index 4e1927a897..a59829b23f 100644 --- a/actionpack/lib/action_view/helpers/form_helper.rb +++ b/actionpack/lib/action_view/helpers/form_helper.rb @@ -655,7 +655,11 @@ module ActionView # <% end %> # # because parameter name repetition is precisely what Rails seeks to distinguish - # the elements of the array. + # the elements of the array. For each item with a checked check box you + # get an extra ghost item with only that attribute, assigned to "0". + # + # In that case it is preferable to either use +check_box_tag+ or to use + # hashes instead of arrays. # # ==== Examples # # Let's say that @post.validated? is 1: -- cgit v1.2.3 From 0d5b50ee3a6d65471f311980b9b6e49fe4b4a021 Mon Sep 17 00:00:00 2001 From: Jeremy Kemper Date: Thu, 19 Mar 2009 03:30:01 -0700 Subject: pluginize concurrent block body part --- actionpack/lib/action_view/base.rb | 4 ++-- .../lib/action_view/body_parts/concurrent_block.rb | 25 ---------------------- 2 files changed, 2 insertions(+), 27 deletions(-) delete mode 100644 actionpack/lib/action_view/body_parts/concurrent_block.rb (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_view/base.rb b/actionpack/lib/action_view/base.rb index 3bbd2ca530..9c0134e7f7 100644 --- a/actionpack/lib/action_view/base.rb +++ b/actionpack/lib/action_view/base.rb @@ -288,12 +288,12 @@ module ActionView #:nodoc: # Access the current template being rendered. # Returns a ActionView::Template object. def template - Thread.current[:_current_render] + @_current_render end def template=(template) #:nodoc: @_first_render ||= template - Thread.current[:_current_render] = template + @_current_render = template end def with_template(current_template) diff --git a/actionpack/lib/action_view/body_parts/concurrent_block.rb b/actionpack/lib/action_view/body_parts/concurrent_block.rb deleted file mode 100644 index 28a3a3bf4d..0000000000 --- a/actionpack/lib/action_view/body_parts/concurrent_block.rb +++ /dev/null @@ -1,25 +0,0 @@ -module ActionView - module BodyParts - class ConcurrentBlock - def initialize(&block) - @block = block - @body = [] - start - end - - def to_s - finish - @body.join - end - - protected - def start - @worker = Thread.new { @block.call(@body) } - end - - def finish - @worker.join if @worker && @worker.alive? - end - end - end -end -- cgit v1.2.3 From f15f1ba285416c12a103716c86f87d593dd3f17b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mislav=20Marohni=C4=87?= Date: Wed, 25 Mar 2009 19:22:45 +0100 Subject: remove piece of UrlWriter documentation claiming that you can access named routes as its class methods This never worked: ActionController::UrlWriter.users_path --- actionpack/lib/action_controller/url_rewriter.rb | 22 +++++----------------- 1 file changed, 5 insertions(+), 17 deletions(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/url_rewriter.rb b/actionpack/lib/action_controller/url_rewriter.rb index bb6cb437b7..16720b915b 100644 --- a/actionpack/lib/action_controller/url_rewriter.rb +++ b/actionpack/lib/action_controller/url_rewriter.rb @@ -68,29 +68,17 @@ module ActionController # This generates, among other things, the method users_path. By default, # this method is accessible from your controllers, views and mailers. If you need # to access this auto-generated method from other places (such as a model), then - # you can do that in two ways. - # - # The first way is to include ActionController::UrlWriter in your class: + # you can do that by including ActionController::UrlWriter in your class: # # class User < ActiveRecord::Base - # include ActionController::UrlWriter # !!! + # include ActionController::UrlWriter # - # def name=(value) - # write_attribute('name', value) - # write_attribute('base_uri', users_path) # !!! + # def base_uri + # user_path(self) # end # end # - # The second way is to access them through ActionController::UrlWriter. - # The autogenerated named routes methods are available as class methods: - # - # class User < ActiveRecord::Base - # def name=(value) - # write_attribute('name', value) - # path = ActionController::UrlWriter.users_path # !!! - # write_attribute('base_uri', path) # !!! - # end - # end + # User.find(1).base_uri # => "/users/1" module UrlWriter def self.included(base) #:nodoc: ActionController::Routing::Routes.install_helpers(base) -- cgit v1.2.3 From 4350e7fe2b9f9205a710888dc2bc5129f10ccd9e Mon Sep 17 00:00:00 2001 From: Jeffrey Hardy Date: Fri, 3 Apr 2009 04:02:56 -0400 Subject: Fix typo in comment: hide_actions -> hide_action --- actionpack/lib/action_controller/base.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'actionpack/lib') diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index c6dd99e959..b24f0bbc26 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -408,7 +408,7 @@ module ActionController #:nodoc: # Return an array containing the names of public methods that have been marked hidden from the action processor. # By default, all methods defined in ActionController::Base and included modules are hidden. - # More methods can be hidden using hide_actions. + # More methods can be hidden using hide_action. def hidden_actions read_inheritable_attribute(:hidden_actions) || write_inheritable_attribute(:hidden_actions, []) end -- cgit v1.2.3