From: Jacob Fugal Date: 2005-10-19T02:48:59+09:00 Subject: Re: Strange error: QtRuby and AR (sqlite3) On 10/18/05, Hans Fugal wrote: > I'm developing a recipe app for my wife using ActiveRecord (with > sqlite3) and QtRuby. It "works" on my iBook, but when I try to test it > on my Debian sarge box I get the following: > > /usr/local/lib/site_ruby/1.8/rubygems.rb:172:in `method_missing': > unresolved method call (ArgumentError) Having the luxury of access to Hans' development environment, I tracked this down. It was a nasty little bugger, and eventually the fault of QtRuby, but the patch here[1] is against rubygems to help gems protect itself against other libraries making mistakes like this. The code in question is from rubygems.rb: # Now add the require_paths to the LOAD_PATH spec.require_paths.each do |path| $:.unshift File.join(spec.full_gem_path, path) end The middle line was throwing the error. Seems really odd for a method_missing error to show up there, right? $:, File and the gemspec are all known quantities... or so we thought. What had happened was that somehow Qt::File had been imported into the current namespace and occluded ::File from core. When Hans' code tried to load a gem, the gems code ended up trying to call Qt::File.join, rather than ::File.join. Qt::File doesn't have a join method, but does handle missing methods in exactly the manner shown in Hans' error. The morals of the story? 1) Don't occlude core libraries 2) Use super as the default behavior for method_missing Regarding 2, if Qt::*'s implementation of method_missing were to bounce up to super when a suitable replacement could not be found, the error probably would have looked something like "NoMethodError: undefined method `join' for Qt::File:Module", rather than the singularly unhelpful "unresolved method call (ArgumentError)". The error would have made it abundantly clear what the problem actually was. Jacob Fugal [1] Patch follows: --- /tmp/rubygems.rb.old 2005-10-18 11:43:11.000000000 -0600 +++ /usr/local/lib/site_ruby/1.8/rubygems.rb 2005-10-18 11:43:32.000000000 -0600 @@ -169,7 +169,7 @@ # Now add the require_paths to the LOAD_PATH spec.require_paths.each do |path| - $:.unshift File.join(spec.full_gem_path, path) + $:.unshift ::File.join(spec.full_gem_path, path) end require spec.autorequire if autorequire && spec.autorequire