好的,所以我发誓这个种子文件以前正在工作,但是现在每当我尝试运行rails db:seed命令时我都会收到错误:
rails aborted!
ActiveRecord::RecordInvalid: Validation failed: Category must exist
/home/krefey/dev/sonar/db/seeds.rb:12:in `<top (required)>'
/home/krefey/dev/sonar/bin/rails:9:in `require'
/home/krefey/dev/sonar/bin/rails:9:in `<top (required)>'
/home/krefey/dev/sonar/bin/spring:15:in `<top (required)>'
bin/rails:3:in `load'
bin/rails:3:in `<main>'
Tasks: TOP => db:seed
我使用的是最新的rails版本,我的数据库是MySQL
我的种子文件是:
Category.create!(name: 'Miniatures')
Category.create!(name: 'Cardgames')
Category.create!(name: 'Boardgames')
Category.create!(name: 'RPG')
Game.create!(name: 'Warhammer 40,000', category_id: Category.find_by(name:'Miniatures'))
Game.create!(name: 'Age of Sigmar', category_id: Category.find_by(name: 'Miniatures'))
Game.create!(name: 'Necromunda', category_id: Category.find_by(name: 'Miniatures'))
Game.create!(name: 'Warmachine', category_id: Category.find_by(name: 'Miniatures'))
Game.create!(name: 'Hordes', category_id: Category.find_by(name: 'Miniatures'))
Game.create!(name: 'Infinity', category_id: Category.find_by(name: 'Miniatures'))
Game.create!(name: 'Munchkin', category_id: Category.find_by(name: 'Cardgames'))
Game.create!(name: 'Cardgamess Against Humanity', category_id: Category.find_by(name: 'Cardgames'))
Game.create!(name: 'Choking Hazard', category_id: Category.find_by(name: 'Cardgames'))
Game.create!(name: 'Poker', category_id: Category.find_by(name: 'Cardgames'))
Game.create!(name: 'Bridge', category_id: Category.find_by(name: 'Cardgames'))
Game.create!(name: 'Risk', category_id: Category.find_by(name: 'Boardgames'))
Game.create!(name: 'Twighlight Imperium', category_id: Category.find_by(name: 'Boardgames'))
Game.create!(name: 'Shadespire', category_id: Category.find_by(name: 'Boardgames'))
Game.create!(name: 'Settlers of Catan', category_id: Category.find_by(name: 'Boardgames'))
Game.create!(name: 'Carcasonne', category_id: Category.find_by(name: 'Boardgames'))
Game.create!(name: 'Dungeons & Dragons', category_id: Category.find_by(name: 'RPG'))
Game.create!(name: 'Pathfinder', category_id: Category.find_by(name: 'RPG'))
Game.create!(name: '7th Sea', category_id: Category.find_by(name: 'RPG'))
Game.create!(name: 'Legend of the 5 Rings', category_id: Category.find_by(name: 'RPG'))
Game.create!(name: 'GURPS', category: Category.find_by(name: 'RPG'))
类别模型:
class Category < ApplicationRecord
has_many :games
validates :name, inclusion: { in: %w(Miniatures RPG Cardgames Boardgames),
message: "%{value} is not a valid game type"}, presence: true
end
游戏模型:
class Game < ApplicationRecord
belongs_to :category
def self.search(search)
where("content LIKE ?", "%#{search}%")
end
end
模式
ActiveRecord::Schema.define(version: 20171130120931) do
create_table "categories", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8" do |t|
t.string "name"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
create_table "games", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8" do |t|
t.string "name"
t.bigint "category_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["category_id"], name: "index_games_on_category_id"
end
add_foreign_key "games", "categories"
end
该错误似乎在抱怨Category.find_by部分。但我不明白为什么。类别模型存在于模式中。我可以成功删除表,创建表并运行迁移,但是当我尝试运行db:seed命令时它会失败(或者它到达db:reset命令的db:seed部分)。
如果我添加
optional: true
游戏模型的代码,然后种子工作,但category_id字段没有填充并显示为nil。那么,我哪里错了?为什么我似乎不能在游戏桌中填充category_id的外键列?
答案 0 :(得分:0)
我认为这样的重构将解决你的堆栈跟踪并使你的种子更具可读性:
?lapply
答案 1 :(得分:0)
我认为你不能将模型对象分配给ID。两种正确的可能性可能是:
Game.create!(name: 'Warhammer 40,000', category: Category.find_by(name:'Miniatures'))
# or also possible, but ugly:
Game.create!(name: 'Warhammer 40,000', category_id: Category.find_by(name:'Miniatures').id)
如AntonTkachov所述,您应该重构代码,以摆脱所有find_by
次调用。
答案 2 :(得分:0)
您可以按照Association proxies in Active Record 所述使用创建,如下所示:
# db/seeds.rb
miniatures = Category.create(name: 'Miniatures')
miniatures.games.create([
{ name: 'Warharmmer 40,000' },
{ name: 'Age of Sigmar' },
{ name: 'Necromunda' }
])
card = Category.create(name: 'Cardgames')
card.games.create([
{ name: 'Muchkin' },
{ name: 'Cardgames Against Humanity' },
{ name: 'Chocking Hazard' }
])
我怀疑你的种子文件以前工作的原因是因为你没有使用Rails 5,这使得belongs_to关联默认需要。有关详细信息,请参阅Abhishek Jain的帖子。