diff options
author | Sean Griffin <sean@seantheprogrammer.com> | 2017-07-17 11:14:11 -0400 |
---|---|---|
committer | Sean Griffin <sean@seantheprogrammer.com> | 2017-07-17 11:19:15 -0400 |
commit | 1519e976b224871c7f7dd476351930d5d0d7faf6 (patch) | |
tree | 994e25c414d75ce825b17cd3c6960b10a3a06c8d /activerecord | |
parent | 828b05f5f9f8decf55170ea75bfdc6d37787993d (diff) | |
download | rails-1519e976b224871c7f7dd476351930d5d0d7faf6.tar.gz rails-1519e976b224871c7f7dd476351930d5d0d7faf6.tar.bz2 rails-1519e976b224871c7f7dd476351930d5d0d7faf6.zip |
Allow multiparameter assigned attributes to be used with `text_field`
Between 4.2 and 5.0 the behavior of how multiparameter attributes
interact with `_before_type_cast` changed. In 4.2 it returns the
post-type-cast value. After 5.0, it returns the hash that gets sent to
the type. This behavior is correct, but will cause an issue if you then
tried to render that value in an input like `text_field` or
`hidden_field`.
In this case, we want those fields to use the post-type-cast form,
instead of the `_before_type_cast` (the main reason it uses
`_before_type_cast` at all is to avoid losing data when casting a
non-numeric string to integer).
I've opted to modify `came_from_user?` rather than introduce a new
method for this as I want to avoid complicating that contract further,
and technically the multiparameter hash didn't come from assignment, it
was constructed internally by AR.
Close #27888.
Diffstat (limited to 'activerecord')
-rw-r--r-- | activerecord/CHANGELOG.md | 5 | ||||
-rw-r--r-- | activerecord/lib/active_record/attribute.rb | 2 | ||||
-rw-r--r-- | activerecord/test/cases/multiparameter_attributes_test.rb | 11 |
3 files changed, 17 insertions, 1 deletions
diff --git a/activerecord/CHANGELOG.md b/activerecord/CHANGELOG.md index 6c7e2b19e7..1bd0199e4c 100644 --- a/activerecord/CHANGELOG.md +++ b/activerecord/CHANGELOG.md @@ -1,3 +1,8 @@ +* Values constructed using multi-parameter assignment will now use the + post-type-cast value for rendering in single-field form inputs. + + *Sean Griffin* + * `Relation#joins` is no longer affected by the target model's `current_scope`, with the exception of `unscoped`. diff --git a/activerecord/lib/active_record/attribute.rb b/activerecord/lib/active_record/attribute.rb index 78662433eb..f89261923b 100644 --- a/activerecord/lib/active_record/attribute.rb +++ b/activerecord/lib/active_record/attribute.rb @@ -174,7 +174,7 @@ module ActiveRecord end def came_from_user? - true + !type.value_constructed_by_mass_assignment?(value_before_type_cast) end end diff --git a/activerecord/test/cases/multiparameter_attributes_test.rb b/activerecord/test/cases/multiparameter_attributes_test.rb index a5f3722be1..aa521e907c 100644 --- a/activerecord/test/cases/multiparameter_attributes_test.rb +++ b/activerecord/test/cases/multiparameter_attributes_test.rb @@ -383,4 +383,15 @@ class MultiParameterAttributeTest < ActiveRecord::TestCase assert_equal("address", ex.errors[0].attribute) end + + def test_multiparameter_assigned_attributes_did_not_come_from_user + topic = Topic.new( + "written_on(1i)" => "1952", + "written_on(2i)" => "3", + "written_on(3i)" => "11", + "written_on(4i)" => "13", + "written_on(5i)" => "55", + ) + refute_predicate topic, :written_on_came_from_user? + end end |