method_missing woes

Hey all, I’m working on a gem that provides archiving functionality to AR models and am trying to allow use of the original’s methods on the archived copies through method missing but I’m getting some really weird errors and can’t for the life of me figure out what’s going on.

my test class structure:

class SomeModel < AR::Base

class Archive < AR::Base

include ArchiveMethods

end

end

module ArchiveMethods

def self.included(base)

base.class_eval do

extend ArchiveClassMethods

protected :get_klass,:get_klass_name,:get_klass_instance_methods

end

end

def method_missing(method,*args,&block)

if get_klass_instance_methods.include?(method.to_s)

instance = get_klass.new

instance.id = self.id

instance_attribute_names = instance.attribute_names

attrs = self.attributes.select{|k,v| instance_attribute_names.include?(k.to_s)}

instance.attributes= attrs,false

instance.send(method,*args,&block)

else

super(method,*args,&block)

end

end

def get_klass

@klass ||= Kernel.const_get(get_klass_name)

end

def get_klass_name

@klass_name ||= self.class.to_s.split(“::”).first

end

def get_klass_instance_methods

@klass_instance_methods ||= get_klass.instance_methods(false)

end

module ArchiveClassMethods;end

end

The error I’m getting is happening in an unrelated test while trying to insert test data into the database:

NoMethodError: undefined method `name’ for nil:NilClass

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/to_sql.rb:57:in `visit_Arel_Nodes_InsertStatement’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/to_sql.rb:56:in `map’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/to_sql.rb:56:in `visit_Arel_Nodes_InsertStatement’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/visitor.rb:15:in `send’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/visitor.rb:15:in `visit’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/visitor.rb:5:in `accept’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/to_sql.rb:19:in `accept’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/connection_adapters/abstract/connection_pool.rb:110:in `with_connection’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/visitors/to_sql.rb:17:in `accept’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/tree_manager.rb:20:in `to_sql’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/arel-2.0.7/lib/arel/select_manager.rb:191:in `insert’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/relation.rb:14:in `send

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/relation.rb:14:in `insert’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/persistence.rb:270:in `create’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/timestamp.rb:47:in `create’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/callbacks.rb:281:in `create’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activesupport-3.0.3/lib/active_support/callbacks.rb:413:in `_run_create_callbacks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/callbacks.rb:281:in `create’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/persistence.rb:246:in `create_or_update’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/callbacks.rb:277:in `create_or_update’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activesupport-3.0.3/lib/active_support/callbacks.rb:413:in `_run_save_callbacks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/callbacks.rb:277:in `create_or_update’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/persistence.rb:39:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/validations.rb:43:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/attribute_methods/dirty.rb:21:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:237:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:289:in `with_transaction_returning_status’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/connection_adapters/abstract/database_statements.rb:139:in `transaction’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:204:in `transaction’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:287:in `with_transaction_returning_status’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:237:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:248:in `rollback_active_record_state!’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/transactions.rb:236:in `save’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/activerecord-3.0.3/lib/active_record/base.rb:498:in `create’

./test/test_helper.rb:66:in `insert_models’

./test/test_base.rb:55:in `__bind_1297269651_315691’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:400:in `call’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:400:in `run_current_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:399:in `each’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:399:in `run_current_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:391:in `run_all_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:395:in `run_parent_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:390:in `run_all_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:395:in `run_parent_setup_blocks’

/Users/tylerpickett/.rvm/gems/ruby-1.8.7-p330@archivist/gems/thoughtbot-shoulda-2.11.1/lib/shoulda/context.rb:379:in `test: The archiving functionality when restoring from the archive with conditions should restore with original id. ’

The only bit of my code there is a method in test_helper:

def insert_models

SomeModel.create(:first_name=>“George”,

:last_name=>“Bush”,

:random_array=>[1,2,3,4],

:some_hash=>{:external_id=>15,

:dog_name=>“Fluffy”})

SomeModel.create(:first_name=>“Bill”,

:last_name=>“Clinton”,

:random_array=>[1,2,3,4],

:some_hash=>{:external_id=>15,

:dog_name=>“Fluffy”})

end

What’s really confusing to me is that these errors persist when running the full test suit after I comment out the method_missing def but go away when I run just the tests that are failing and stay gone until I put method missing back in.