This project is archived and is in readonly mode.
has_many :conditions => 'id = #{id}' interpolation doesn't work when :dependent => :delete_all is set
Reported by Brad Gessler | March 10th, 2011 @ 09:19 AM
When providing an interpolated value to the :conditions key in a has_many association where the :dependent key is set to :delete_all
has_many :clients_with_interpolated_conditions, :class_name => "Client", :conditions => 'rating > #{rating}', :dependent => :delete_all
AR would not interpolate the :conditions string and cause the
DELETE query to fail (You end up with SQL that looks like
DELETE * FROM clients WHERE rating > #{rating}
instead of DELETE * FROM clients WHERE rating >
4
)
I patched AR to call the record's interpolate_sql method on the :conditions string.
I believe this is a regression issue between introduced in 2.3.6 and effects all subsequent 2.3.x releases.
Comments and changes to this ticket
-
Brad Gessler March 10th, 2011 @ 09:54 PM
- Title changed from has_many :conditions => 'id = #{id}' interpolation doesn't work when :dependent => :delete_all is to has_many :conditions => 'id = #{id}' interpolation doesn't work when :dependent => :delete_all is set
- Assigned user set to Andrew White
-
Andrew White March 10th, 2011 @ 10:07 PM
- Importance changed from to Low
Does it only affect 2.3.x?
-
Brad Gessler March 10th, 2011 @ 10:51 PM
It effects the 3.0.x branch as well. Here's what one of those failures look like:
5) Error: test_dependence_with_missing_association(HasOneAssociationsTest): ActiveRecord::StatementInvalid: SQLite3::SQLException: unrecognized token: "#": DELETE FROM "companies" WHERE ((("companies"."type" = 'Client' OR "companies"."type" = 'SpecialClient') OR "companies"."type" = 'VerySpecialClient')) AND ((firm_id = 1) AND (rating > #{rating})) /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract_adapter.rb:207:in `log' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/sqlite_adapter.rb:135:in `execute_without_query_record' ./test/cases/helper.rb:35:in `execute' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract/database_statements.rb:284:in `update_sql' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/sqlite_adapter.rb:139:in `update_sql' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract/database_statements.rb:289:in `delete_sql' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/sqlite_adapter.rb:145:in `delete_sql' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract/database_statements.rb:54:in `delete' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract/query_cache.rb:16:in `delete' /Library/Ruby/Gems/1.8/gems/arel-2.0.9/lib/arel/crud.rb:34:in `delete' /Users/bgessler/Projects/rails/activerecord/lib/active_record/relation.rb:273:in `delete_all' /Users/bgessler/Projects/rails/activerecord/lib/active_record/relation.rb:273:in `delete_all' /Users/bgessler/Projects/rails/activerecord/lib/active_record/base.rb:439:in `__send__' /Users/bgessler/Projects/rails/activerecord/lib/active_record/base.rb:439:in `delete_all' /Users/bgessler/Projects/rails/activerecord/lib/active_record/associations.rb:1718:in `delete_all_has_many_dependencies' /Users/bgessler/Projects/rails/activerecord/lib/active_record/associations.rb:1629:in `send' /Users/bgessler/Projects/rails/activerecord/lib/active_record/associations.rb:1629:in `_callback_before_391' /Users/bgessler/Projects/rails/activesupport/lib/active_support/callbacks.rb:429:in `_run_destroy_callbacks' /Users/bgessler/Projects/rails/activerecord/lib/active_record/callbacks.rb:260:in `destroy' /Users/bgessler/Projects/rails/activerecord/lib/active_record/transactions.rb:235:in `destroy' /Users/bgessler/Projects/rails/activerecord/lib/active_record/transactions.rb:292:in `with_transaction_returning_status' /Users/bgessler/Projects/rails/activerecord/lib/active_record/connection_adapters/abstract/database_statements.rb:139:in `transaction' /Users/bgessler/Projects/rails/activerecord/lib/active_record/transactions.rb:207:in `transaction' /Users/bgessler/Projects/rails/activerecord/lib/active_record/transactions.rb:290:in `with_transaction_returning_status' /Users/bgessler/Projects/rails/activerecord/lib/active_record/transactions.rb:235:in `destroy' ./test/cases/associations/has_one_associations_test.rb:250:in `test_dependence_with_missing_association' /Users/bgessler/Projects/rails/activesupport/lib/active_support/testing/setup_and_teardown.rb:67:in `__send__' /Users/bgessler/Projects/rails/activesupport/lib/active_support/testing/setup_and_teardown.rb:67:in `run' /Users/bgessler/Projects/rails/activesupport/lib/active_support/callbacks.rb:418:in `_run_setup_callbacks' /Users/bgessler/Projects/rails/activesupport/lib/active_support/testing/setup_and_teardown.rb:65:in `run'
I've attached a patch for 3.0.x.
-
Brad Gessler March 11th, 2011 @ 12:03 AM
- Tag changed from rails 2.3.11, activerecord, regression to rails 2.3.11, rails 3.0.4, activerecord, regression
-
Dan Pickett March 12th, 2011 @ 05:20 PM
- State changed from new to open
Hey Brad,
The fix looks good, but the 3.0.x patch no longer applies cleanly to edge - would you mind updating so your authorship is preserved?
-
Brad Gessler March 12th, 2011 @ 07:27 PM
Single quote string interpolation is deprecated in the edge build in favor of procs (good!) which fixes this issue. This patch just adds :delete_all to the test that was failing before (should prevent this type of bug from happening again).
Create your profile
Help contribute to this project by taking a few moments to create your personal profile. Create your profile »
<h2 style="font-size: 14px">Tickets have moved to Github</h2>
The new ticket tracker is available at <a href="https://github.com/rails/rails/issues">https://github.com/rails/rails/issues</a>