diff options
| author | Ryuta Kamizono <kamipo@gmail.com> | 2019-04-21 21:54:32 +0900 | 
|---|---|---|
| committer | Ryuta Kamizono <kamipo@gmail.com> | 2019-04-21 21:54:32 +0900 | 
| commit | f9326e567ca0d9fe957e70de821a0a644b0b441d (patch) | |
| tree | b5a2826a853a6a810d18e736e82eea4cb7f4761f /activerecord/lib/active_record/attribute_methods | |
| parent | 96cf7e0e676c54cb8177de146efa27ed49c4b8c6 (diff) | |
| download | rails-f9326e567ca0d9fe957e70de821a0a644b0b441d.tar.gz rails-f9326e567ca0d9fe957e70de821a0a644b0b441d.tar.bz2 rails-f9326e567ca0d9fe957e70de821a0a644b0b441d.zip  | |
Avoid method call if `@transaction_state` is not finalized
Method call in Ruby is a bit slow.
This makes attribute access 10% faster by avoiding method call
(`sync_with_transaction_state`).
Before (96cf7e0e):
```
Warming up --------------------------------------
             user.id   131.291k i/100ms
          user['id']    91.786k i/100ms
           user.name   151.605k i/100ms
        user['name']    92.664k i/100ms
       user.changed?    17.772k i/100ms
 user.saved_changes?    23.909k i/100ms
Calculating -------------------------------------
             user.id      1.988M (± 7.0%) i/s -      9.978M in   5.051474s
          user['id']      1.155M (± 5.8%) i/s -      5.783M in   5.022672s
           user.name      2.450M (± 4.3%) i/s -     12.280M in   5.021234s
        user['name']      1.263M (± 2.1%) i/s -      6.394M in   5.066638s
       user.changed?    175.070k (±13.3%) i/s -    853.056k in   5.011555s
 user.saved_changes?    259.114k (±11.8%) i/s -      1.267M in   5.001260s
```
After (this change):
```
Warming up --------------------------------------
             user.id   137.625k i/100ms
          user['id']    96.054k i/100ms
           user.name   156.379k i/100ms
        user['name']    94.795k i/100ms
       user.changed?    18.172k i/100ms
 user.saved_changes?    24.337k i/100ms
Calculating -------------------------------------
             user.id      2.201M (± 0.5%) i/s -     11.010M in   5.002955s
          user['id']      1.320M (± 1.0%) i/s -      6.628M in   5.021293s
           user.name      2.677M (± 1.6%) i/s -     13.449M in   5.024399s
        user['name']      1.314M (± 1.8%) i/s -      6.636M in   5.051444s
       user.changed?    190.588k (±11.1%) i/s -    944.944k in   5.065848s
 user.saved_changes?    262.782k (±12.1%) i/s -      1.290M in   5.028080s
```
Diffstat (limited to 'activerecord/lib/active_record/attribute_methods')
4 files changed, 8 insertions, 8 deletions
diff --git a/activerecord/lib/active_record/attribute_methods/before_type_cast.rb b/activerecord/lib/active_record/attribute_methods/before_type_cast.rb index affcf2a4db..3d917ec9b1 100644 --- a/activerecord/lib/active_record/attribute_methods/before_type_cast.rb +++ b/activerecord/lib/active_record/attribute_methods/before_type_cast.rb @@ -46,7 +46,7 @@ module ActiveRecord        #   task.read_attribute_before_type_cast('completed_on') # => "2012-10-21"        #   task.read_attribute_before_type_cast(:completed_on)  # => "2012-10-21"        def read_attribute_before_type_cast(attr_name) -        sync_with_transaction_state +        sync_with_transaction_state if @transaction_state&.finalized?          @attributes[attr_name.to_s].value_before_type_cast        end @@ -61,7 +61,7 @@ module ActiveRecord        #   task.attributes_before_type_cast        #   # => {"id"=>nil, "title"=>nil, "is_done"=>true, "completed_on"=>"2012-10-21", "created_at"=>nil, "updated_at"=>nil}        def attributes_before_type_cast -        sync_with_transaction_state +        sync_with_transaction_state if @transaction_state&.finalized?          @attributes.values_before_type_cast        end @@ -73,7 +73,7 @@ module ActiveRecord          end          def attribute_came_from_user?(attribute_name) -          sync_with_transaction_state +          sync_with_transaction_state if @transaction_state&.finalized?            @attributes[attribute_name].came_from_user?          end      end diff --git a/activerecord/lib/active_record/attribute_methods/dirty.rb b/activerecord/lib/active_record/attribute_methods/dirty.rb index 942fe48635..444568562b 100644 --- a/activerecord/lib/active_record/attribute_methods/dirty.rb +++ b/activerecord/lib/active_record/attribute_methods/dirty.rb @@ -157,12 +157,12 @@ module ActiveRecord        private          def mutations_from_database -          sync_with_transaction_state +          sync_with_transaction_state if @transaction_state&.finalized?            super          end          def mutations_before_last_save -          sync_with_transaction_state +          sync_with_transaction_state if @transaction_state&.finalized?            super          end diff --git a/activerecord/lib/active_record/attribute_methods/read.rb b/activerecord/lib/active_record/attribute_methods/read.rb index 84b1ec2fea..409a150e56 100644 --- a/activerecord/lib/active_record/attribute_methods/read.rb +++ b/activerecord/lib/active_record/attribute_methods/read.rb @@ -39,7 +39,7 @@ module ActiveRecord        # This method exists to avoid the expensive primary_key check internally, without        # breaking compatibility with the read_attribute API        def _read_attribute(attr_name, &block) # :nodoc -        sync_with_transaction_state +        sync_with_transaction_state if @transaction_state&.finalized?          @attributes.fetch_value(attr_name.to_s, &block)        end diff --git a/activerecord/lib/active_record/attribute_methods/write.rb b/activerecord/lib/active_record/attribute_methods/write.rb index d1cfe43bb2..6a21643884 100644 --- a/activerecord/lib/active_record/attribute_methods/write.rb +++ b/activerecord/lib/active_record/attribute_methods/write.rb @@ -43,14 +43,14 @@ module ActiveRecord        # This method exists to avoid the expensive primary_key check internally, without        # breaking compatibility with the write_attribute API        def _write_attribute(attr_name, value) # :nodoc: -        sync_with_transaction_state +        sync_with_transaction_state if @transaction_state&.finalized?          @attributes.write_from_user(attr_name.to_s, value)          value        end        private          def write_attribute_without_type_cast(attr_name, value) -          sync_with_transaction_state +          sync_with_transaction_state if @transaction_state&.finalized?            @attributes.write_cast_value(attr_name.to_s, value)            value          end  | 
