aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorXavier Noria <fxn@hashref.com>2008-06-17 21:59:41 +0200
committerXavier Noria <fxn@hashref.com>2008-06-17 21:59:41 +0200
commitea40dc09a564ebc2b0034e3c1ae2c4daffe7e79b (patch)
tree9ef14ff2be90ae11f5e64e617ffb9ec71606d8fb
parent235cd218b692d5a648a03cf574f5a049202845ea (diff)
downloadrails-ea40dc09a564ebc2b0034e3c1ae2c4daffe7e79b.tar.gz
rails-ea40dc09a564ebc2b0034e3c1ae2c4daffe7e79b.tar.bz2
rails-ea40dc09a564ebc2b0034e3c1ae2c4daffe7e79b.zip
provide a more complete explanation about why the check_box generates a hidden field, and document the problem with array-like parameters
-rw-r--r--actionpack/lib/action_view/helpers/form_helper.rb33
1 files changed, 31 insertions, 2 deletions
diff --git a/actionpack/lib/action_view/helpers/form_helper.rb b/actionpack/lib/action_view/helpers/form_helper.rb
index 7d85799038..6348ff5f49 100644
--- a/actionpack/lib/action_view/helpers/form_helper.rb
+++ b/actionpack/lib/action_view/helpers/form_helper.rb
@@ -449,8 +449,37 @@ module ActionView
# assigned to the template (identified by +object+). It's intended that +method+ returns an integer and if that
# integer is above zero, then the checkbox is checked. Additional options on the input tag can be passed as a
# hash with +options+. The +checked_value+ defaults to 1 while the default +unchecked_value+
- # is set to 0 which is convenient for boolean values. Since HTTP standards say that unchecked checkboxes don't post anything,
- # we add a hidden value with the same name as the checkbox as a work around.
+ # is set to 0 which is convenient for boolean values.
+ #
+ # === Gotcha
+ #
+ # 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
+ # invoice the user unchecks its check box, no +paid+ parameter is sent. So,
+ # any mass-assignment idiom like
+ #
+ # @invoice.update_attributes(params[:invoice])
+ #
+ # 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.
+ #
+ # Unfortunately that workaround does not work when the check box goes
+ # within an array-like parameter, as in
+ #
+ # <% fields_for "project[invoice_attributes][]", invoice, :index => nil do |form| %>
+ # <%= form.check_box :paid %>
+ # ...
+ # <% end %>
+ #
+ # because parameter name repetition is precisely what Rails seeks to distinguish
+ # the elements of the array.
#
# ==== Examples
# # Let's say that @post.validated? is 1: