2013-04-28 54 views
10

我有3個模型,用戶,遊戲和玩家。用戶和遊戲之間基本上有多對多的關係,玩家作爲連接表,除了玩家有其他信息,所以它有自己的模型。shoulda matchers should validate_uniqueness_of failing with scope

玩家需要的遊戲ID和用戶ID的獨特組合,所以我試圖在球員說:

validates_uniqueness_of :user_id, :scope => :game_id 

,然後在我的天賦,我說(用早該的匹配):

it { should validate_uniqueness_of(:user_id).scoped_to(:game_id)} 

這裏是玩家定義的關係:

belongs_to :game, :inverse_of => :players 
belongs_to :user, :inverse_of => :players 

但我得到一個ActiveRecord :: statemen該規格的tinvalid錯誤

ActiveRecord::StatementInvalid: Mysql2::Error: Column 'game_id' cannot be null: INSERT INTO `players` ETC... 

任何想法發生了什麼問題?

回答

9

這是一個known issue。如果範圍字段取決於型號並且也設置爲:null => false,則會出現此錯誤。

另外,不要看看rails Column cannot be null:

+0

感謝。沒有意識到那個bug在那裏。 – bdwain 2013-04-28 22:24:01

+1

更新:這將在v 2.7中修復。見:https://github.com/thoughtbot/shoulda-matchers/commit/e3493811865a42b4bebcf0d3001333b9d4cb5208 – 2014-07-19 00:10:21

6

雖然這是一個已知的問題,有辦法解決它。

如果您先創建一條記錄,然後測試唯一性驗證,那麼它將起作用。

所以,而不是簡單地寫

it { should validate_uniqueness_of(:user_id) } 

你可以寫

it do 
    FactoryGirl.create(:player) 
    should validate_uniqueness_of(:user_id) 
end 

而獨特的驗證規範將正常工作。

參考:http://rubydoc.info/github/thoughtbot/shoulda-matchers/master/frames

+3

或'it {expect(create(:label))。to validate_uniqueness_of(:value).scoped_to(:question_id)}'在rspec3語法的一條平滑線上。 – 2014-03-06 15:55:01

1

你可以閱讀官方的源代碼警告here

一種解決方案是提到的問題和解決方法:

describe Player do 
    describe "validations" do 
    it do 
     expect(Player.new(game_id: 1)). 
     to validate_uniqueness_of(:user_id). 
     scoped_to(:game_id) 
    end 
    end 
end 
相關問題