遇到has_many / belongs_to关系有问题,“不能写未知属性”

时间:2017-03-19 00:04:54

标签: ruby-on-rails ruby activerecord

基本思路是这样的:我有一个Board课,有两名球员和一名现任球员。我希望能够@board.current_player并让它返回Player的实例,而现在,它已设置为@board.current_player_id返回播放器的ID,我必须查询该ID以获取current_player。

这是我的课程

class Board < ActiveRecord::Base
  has_one :player1, class_name: 'Player'
  has_one :player2, class_name: 'Player'
  has_one :current_player, class_name 'Player'
end

class Player < ActiveRecord::Base
  belongs_to :board
end

这是迁移

class CreatePlayersAndBoard < ActiveRecord::Migration
  def change 
    create_table :boards do |t|
      t.references :current_player, references: :players
    end

    create_table :players do |t|
      t.belongs_to :board, index: true
    end
  end 
end

根据has_one关联的RailsGuides条目。

@board.player1@board.player2都会返回一个播放器实例,但由于current_player的ID存在于boards表中,因此它似乎不是has_one|belongs_to 1}}关系正在发挥作用。

我很想知道究竟是什么让ActiveRecord返回一个实例而不是一个ID - 我一直以为它要么在ActiveRecord Association的一边,要么在迁移中我和我在一起。我很难确切地知道在哪里。

也许这是一种反模式,我应该存储在其他地方确定当前玩家的逻辑,但经过一番思考后,这仍然感觉就像是正确的位置。

1 个答案:

答案 0 :(得分:1)

在您的电路板模型中,您有has_one :current_player,因此当您执行此操作时,它将运行此类查询。

irb(main):008:0> board.current_player
Player Load (0.2ms)  SELECT  "players".* FROM "players" WHERE "players"."board_id" = $1 LIMIT 1  [["board_id", 1]]

如果你想将current_player_id保存在你的董事会议席表中那么你将不得不做这样的事情

class Board < ActiveRecord::Base
  has_one :player1, class_name: 'Player'
  has_one :player2, class_name: 'Player'

  def current_player
    Player.find(current_player_id)
  end
end