Rails关联=返回值和行为

时间:2016-09-30 06:47:01

标签: ruby-on-rails associations

该指南未说明data "terraform_remote_state" "base_networking" { backend = "s3" config { bucket = "${var.remote_state_bucket}" region = "${var.remote_state_region}" key = "${var.networking_remote_state_key}" } } [...] vpc_id = "${data.terraform_remote_state.base_networking.vpc_id}" 方法的返回值。例如has_one association=

对于简单的情况,它返回指定的对象。但是,只有在分配成功时才会这样做。

有时association=会立即保留数据库中的更改,例如设置has_one关联的持久记录。

  • association=如何对分配失败做出反应? (我可以判断它是否失败了吗?)
  • 有爆炸声!失败引发异常的版本?

3 个答案:

答案 0 :(得分:1)

  

关联如何对分配失败做出反应? (我可以判断它是否失败了吗?)

它不会失败。无论你分配什么,它都将按预期工作:

  

在幕后,这意味着从中提取主键   对象并将关联对象的外键设置为相同的对象   值。

或者将关联保存为传入对象的字符串表示形式,如果对象是"无效"。

  

有爆炸声!失败引发异常的版本?

不,没有。

答案 1 :(得分:0)

association=不应该失败。它是对属性属性的简单分配。此方法没有调用任何验证,并且在您调用save之前,连接不会保留在数据库中。

作业的返回值是您传递给它的值。

答案 2 :(得分:0)

http://guides.rubyonrails.org/association_basics.html#has-one-association-reference-when-are-objects-saved-questionmark

因此,指南的另一部分确实讨论了关联分配的返回行为。

如果关联分配失败,则返回false。 没有爆炸版本。

更新

周围的行为:has_many / has_one through似乎有所不同。

演示存储库:https://github.com/lulalalalistia/association-assignment-demo

在演示中,我在第一次提交中播种了一些数据,在第二次提交时播放了硬编码验证错误。演示正在使用rails 4.2

has_many通过

class Boss < ActiveRecord::Base
  has_many :room_ownerships, as: :owner
  has_many :rooms, through: :room_ownerships
end

当我添加房间时,会引发异常:

irb(main):008:0> b.rooms << Room.first
  Boss Load (0.2ms)  SELECT  "bosses".* FROM "bosses"  ORDER BY "bosses"."id" ASC LIMIT 1
  Room Load (0.1ms)  SELECT  "rooms".* FROM "rooms"  ORDER BY "rooms"."id" ASC LIMIT 1
   (0.1ms)  begin transaction
   (0.1ms)  rollback transaction
ActiveRecord::RecordInvalid: Validation failed: foo
irb(main):014:0> b.rooms
=> #<ActiveRecord::Associations::CollectionProxy []>

has_one through

class Employee < ActiveRecord::Base
  has_one :room_ownership, as: :owner
  has_one :room, through: :room_ownership
end

当我添加一个房间时,我不会例外:

irb(main):021:0> e.room = Room.first
  Room Load (0.2ms)  SELECT  "rooms".* FROM "rooms"  ORDER BY "rooms"."id" ASC LIMIT 1
  RoomOwnership Load (0.1ms)  SELECT  "room_ownerships".* FROM "room_ownerships" WHERE "room_ownerships"."owner_id" = ? AND "room_ownerships"."owner_type" = ? LIMIT 1  [["owner_id", 1], ["owner_type", "Employee"]]
   (0.1ms)  begin transaction
   (0.1ms)  rollback transaction
=> #<Room id: 1, created_at: "2016-10-03 02:32:33", updated_at: "2016-10-03 02:32:33">
irb(main):022:0> e.room
=> #<Room id: 1, created_at: "2016-10-03 02:32:33", updated_at: "2016-10-03 02:32:33">

这使得很难看出作业是否成功。