Rails 第一次将属性分配给我的模型时抛出错误

Rails is throwing an error the first time an attribute is assigned to my model

我有一个 rails 模型可以跟踪应用程序中的其他模型。 (不寻常,但对于这个项目是必要的)。

当我尝试分配属性 model_name 时,出现一次错误,但之后不会再发生。

AppModel
model_name   created_at   updated_at
----------------------------------------
User 
Question
Post
Answer     

在控制台中,我收到一个奇怪的错误:

> model = AppModel.new
> model.model_name = "User"  # First time causes the error.
> model.model_name = "User"  # Second time it works.

错误:

ActiveRecord::DangerousAttributeError: record_changed? is defined by Active Record
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activerecord-4.1.4/lib/active_record/attribute_methods.rb:104:in `instance_method_already_implemented?'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:288:in `block in define_attribute_method'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:285:in `each'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:285:in `define_attribute_method'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:252:in `block in define_attribute_methods'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:252:in `each'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activemodel-4.1.4/lib/active_model/attribute_methods.rb:252:in `define_attribute_methods'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activerecord-4.1.4/lib/active_record/attribute_methods.rb:75:in `block in define_attribute_methods'
    from /Users/donaldpinkus/.rvm/rubies/ruby-2.1.5/lib/ruby/2.1.0/mutex_m.rb:73:in `synchronize'
    from /Users/donaldpinkus/.rvm/rubies/ruby-2.1.5/lib/ruby/2.1.0/mutex_m.rb:73:in `mu_synchronize'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activerecord-4.1.4/lib/active_record/attribute_methods.rb:72:in `define_attribute_methods'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activerecord-4.1.4/lib/active_record/attribute_methods.rb:196:in `method_missing'
    from (irb):3
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/railties-4.1.4/lib/rails/commands/console.rb:90:in `start'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/railties-4.1.4/lib/rails/commands/console.rb:9:in `start'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/railties-4.1.4/lib/rails/commands/commands_tasks.rb:69:in `console'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/railties-4.1.4/lib/rails/commands/commands_tasks.rb:40:in `run_command!'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/railties-4.1.4/lib/rails/commands.rb:17:in `<top (required)>'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:247:in `require'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:247:in `block in require'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:232:in `load_dependency'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:247:in `require'
    from /Users/donaldpinkus/Projects/hooker/bin/rails:8:in `<top (required)>'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:241:in `load'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:241:in `block in load'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:232:in `load_dependency'
    from /Users/donaldpinkus/.rvm/gems/ruby-2.1.5/gems/activesupport-4.1.4/lib/active_support/dependencies.rb:241:in `load'
    from /Users/donaldpinkus/.rvm/rubies/ruby-2.1.5/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:54:in `require'
    from /Users/donaldpinkus/.rvm/rubies/ruby-2.1.5/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:54:in `require'
    from -e:1:in `<main>'2.1.5 :004 > e.model_name = "User"
 => "User"

"model_name" 不是模型的保留字,所以这里发生了什么?

发生这种情况是因为在 ActiveRecord 模型中已经有一个方法,它被准确地称为 model_name,returns(显然)这个模型的名称(除其他外)。

  • From: .../ruby-2.1.5/gems/activemodel-4.2.0/lib/active_model/naming.rb @ line 222:
  • Owner: ActiveModel::Naming
  • Visibility: public
  • Signature: model_name()
  • Number of lines: 12

Returns an ActiveModel::Name object for module. It can be used to retrieve all kinds of naming-related information (See ActiveModel::Name for more information).

当 ActiveRecord 从 table 中获取对象时,它还会创建名称与 table 中的列名称相对应的方法。发生的事情是它获取一个对象,在给定对象上看到一个列 model_name,尝试定义一个方法 model_name 并突然发现它已经存在。

注意事项:避免不必要的长属性名称。如果你在模型中定义一个名称,它可以只是 name,它的范围是 "model" class 无论如何,显然它是模型的名称。

但是,错误报告代码可能包含需要追踪的错误。