On Tue, 13 Dec 2005, Ara.T.Howard wrote:
<snip>
i added some code to see how callbacks.rb was getting loaded and see that it's
gettting loaded twice. if you read the code and the way is uses alias_method
you will see that it is __very__ bad for this code the get loaded twice as it
sets up a recursive definition of ActiveRecord::Base::instantiate via
alias_method :instantiate_without_callbacks, :instantiate
alias_method :instantiate, :instantiate_with_callbacks
this kind of thing exists in other places in the code as well. here are
summaries of the two stack traces when this code is loaded:
file : require.1.yml
---
- /usr/local/bin/irb:13
- "/usr/local/lib/ruby/1.8/irb.rb:54:in `start'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:21:in `setup'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:216:in `load_modules'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:216:in `each'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:218:in `load_modules'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:218:in `require'"
- "./script/../config/../config/environment.rb:8"
- "./script/../config/../config/environment.rb:8:in `require'"
- "./script/../config/../config/boot.rb:16"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:4:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:88:in
`search_gempath'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:88:in
`each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:90:in
`search_gempath'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:158:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:158:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:150:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require__'"
-
/usr/local/lib/ruby/gems/1.8/gems/actionpack-1.11.1/lib/action_controller.rb:50
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:214:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require__'"
-
/usr/local/lib/ruby/gems/1.8/gems/actionpack-1.11.1/lib/action_controller/caching.rb:518
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:194:in
`const_missing'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:178:in
`require_dependency'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:178:in
`require_dependency'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:22:in
`depend_on'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:39:in
`require_or_load'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:207:in
`load'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:207:in
`load'"
-
/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53:in
`class_eval'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53:in
`class_eval'"
-
/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:56
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:56:in
`include'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record/callbacks.rb:180:in
`append_features'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record/callbacks.rb:180:in
`open'"
file : require.2.yml
---
- /usr/local/bin/irb:13
- "/usr/local/lib/ruby/1.8/irb.rb:54:in `start'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:21:in `setup'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:216:in `load_modules'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:216:in `each'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:218:in `load_modules'"
- "/usr/local/lib/ruby/1.8/irb/init.rb:218:in `require'"
- "./script/../config/../config/environment.rb:8"
- "./script/../config/../config/environment.rb:8:in `require'"
- "./script/../config/../config/boot.rb:16"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:4:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:88:in
`search_gempath'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:88:in
`each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:90:in
`search_gempath'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:158:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:157:in `each'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:158:in `activate'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems.rb:150:in `activate'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activesupport-1.2.4/lib/active_support/dependencies.rb:214:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require'"
- "/usr/local/lib/ruby/site_ruby/1.8/rubygems/loadpath_manager.rb:5:in
`require__'"
-
/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53:in
`class_eval'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:53:in
`class_eval'"
-
/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:56
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record.rb:56:in
`include'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record/callbacks.rb:180:in
`append_features'"
-
"/usr/local/lib/ruby/gems/1.8/gems/activerecord-1.13.1/lib/active_record/callbacks.rb:180:in
`open'"
yikes. basically what is happening is that Callbacks gets mixed into
ActiveRecord::Base __twice__ - setting up a recursive defintion of
#instantiate (the second time).
the first time is triggered from
/usr/local/lib/ruby/gems/1.8/gems/actionpack-1.11.1/lib/action_controller/caching.rb:518
which reads
if defined?(ActiveRecord::Observer)
and triggers a load of active_record.rb via the const missing hack.
the second loading is the explicit loading the initializer does.
now, why this seems to be platform dependant i do not understand yet - but the
combination of autoloading hooks, require overrides, and non-protected (unless
defined?...) class defs and method aliases seem fragile.
i'm trying to fix - but it seems a wholesale revamp of the loading methods and
definition strategy is in order. on the otherhand an __early__ subversion of
require to occur exactly once no matter what might short circuirt the whole
thing...
thoughts?
-a
--
===============================================================================
| ara [dot] t [dot] howard [at] noaa [dot] gov
| all happiness comes from the desire for others to be happy. all misery
| comes from the desire for oneself to be happy.
| -- bodhicaryavatara
===============================================================================
_______________________________________________
Rails-core mailing list
[email protected]
http://lists.rubyonrails.org/mailman/listinfo/rails-core