:apps / 'apps' 是否保留在 Rails v4 中?

Is :apps / 'apps' reserved in Rails v4?

我 运行 在尝试进行批量更新时遇到奇怪的错误:

rake db:caching:stats:calculate
rake aborted!
NoMethodError: undefined method `each' for 2548:Fixnum
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/associations/collection_association.rb:365:in `replace'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/associations/collection_association.rb:47:in `writer'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/associations/builder/association.rb:123:in `apps='
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/attribute_assignment.rb:54:in `public_send'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/attribute_assignment.rb:54:in `_assign_attribute'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/attribute_assignment.rb:41:in `block in assign_attributes'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/attribute_assignment.rb:35:in `each'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/attribute_assignment.rb:35:in `assign_attributes'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/persistence.rb:251:in `block in update'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/transactions.rb:351:in `block in with_transaction_returning_status'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/connection_adapters/abstract/database_statements.rb:213:in `block in transaction'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/connection_adapters/abstract/transaction.rb:184:in `within_new_transaction'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/connection_adapters/abstract/database_statements.rb:213:in `transaction'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/transactions.rb:220:in `transaction'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/transactions.rb:348:in `with_transaction_returning_status'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/persistence.rb:250:in `update'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/relation.rb:369:in `update'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/relation.rb:366:in `block in update'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/relation.rb:366:in `map'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/relation.rb:366:in `with_index'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/relation.rb:366:in `update'
/usr/local/rvm/gems/ruby-2.2.1/gems/activerecord-4.2.4/lib/active_record/querying.rb:8:in `update'
/home/ubuntu/workspace/pf_middleware/lib/tasks/caching/calculate_stats.rake:42:in `block (4 levels) in <top (required)>'
Tasks: TOP => db:caching:stats:calculate

我正在生成相当大的更新集,所以我使用以下内容来确保我传递了我预期的内容并产生了相同的错误。

School.update([1,2,3], [{apps: 11111},{apps: 22222},{apps: 33333}])
==> NoMethodError: undefined method `each' for 11111:Fixnum

我检查并重新检查了文档,尝试 'apps' 而不是 :apps。仔细检查了 apps 是 School 等中的字段,但无法理解为什么我一直收到此错误。

我决定尝试一个不同的领域......而且成功了!

hash = { 1 => { offers: 123 }, 2 => { offers: 321 } }
School.update(hash.keys, hash.values)

这让我相信 :apps / 'apps' 是一些特别的东西,但我找不到证明这一点的证据。有人有什么想法吗?

谢谢!

与“:apps”无关。此语法无效:

2 => :apps => 321

键值对可以使用old-style语法,例如

{:apps => 123}

或新式语法糖:

{apps: 123}

但是,它们只有两个:一个键和一个值。你不能说

 {2 => :apps => 321}

但是,您可以将散列作为键或值,因此您可以

 {2 => {:apps => 321}}

 {{2 => :apps} => 321}

在你的情况下,你的意思似乎是

hash = { 1 => { :apps => 123 }, 2 => {:apps => 321 } }

我想你刚刚错过了一个 {

好的,自从我的第一个回答以来你完全改变了你的问题,这里是另一个问题。

当你这样做时

School.update([1,2,3], [{apps: 11111},{apps: 22222},{apps: 33333}])

就像在说

School.find(1).update_attributes({apps: 11111})
School.find(1).update_attributes({apps: 22222})
School.find(1).update_attributes({apps: 33333})

当你说

School.find(1).update_attributes({apps: 11111})

你实际上是在说

school = School.find(1)
school.apps = 11111
school.save

如果你的学校 class 没有名为 "apps=" 的实例方法,或者它有但该方法不需要整数,它将引发异常(或在后者中情况下,可能会产生不可预知的结果)。

在这种情况下,如果 school has_many :apps 那么 "School#apps=" 方法是由 has_many 关联设置的方法,并且需要一个 App 对象数组。