当我尝试 运行 种子脚本时收到错误消息
Getting an error message when I attempt to run seed script
Rails 5.1
在我的 seeds.rb 文件中我有:
user = User.new(
:email =>'random@myapp.com',
:password =>'xK#986754',
:password_confirmation =>'xK#986754',
:first_name =>'John',
:last_name =>'Smith',
:role => 1
:approved => true
)
user.skip_invitation
user.save
在我的 user.rb 模型中,我有:
class User < ActiveRecord::Base
enum role: [:user, :vip, :admin]
after_initialize :set_default_role, :if => :new_record?
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable
devise :invitable, :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
attr_accessor :email, :password, :first_name, :last_name, :role, :approved
validates :email, uniqueness: true, presence: true
validates :first_name, presence: true
validates :last_name, presence: true
validates :role, presence: true
def set_default_role
self.role ||= :user
end
end
在我的迁移文件中,我有:
class DeviseCreateUsers < ActiveRecord::Migration[5.1]
def change
create_table :users do |t|
t.string :first_name, null: false
t.string :last_name, null: false
t.integer :role, null: false
t.string :email, null: false
## Approved
t.boolean :approved, :default => 0, :null => false
当我尝试 运行 种子文件时,我收到以下错误消息:
ActiveRecord::NotNullViolation: Mysql2::Error: Field 'first_name' doesn't have a default value: INSERT INTO `users` (`approved`, `created_at`, `updated_at`) VALUES (1, '2017-10-23 02:23:36', '2017-10-23 02:23:36')
我显然在使用这个装置gem
有什么想法吗?
删除您的 attr_accessor
行。 attr_accessor
用于声明在 class 中包装实例变量的简单 getter/setter 方法,它不能与要保存到数据库的属性的 Rails 模型一起使用。这实际上意味着所有 attr_accessor
属性仅存在于内存中,您的模型永远不会尝试将它们写入数据库,因此您的错误消息和插入查询中的所有缺失值。
您没有提供名字值,并且您已告诉数据库不允许为空但没有给出默认值。
那么,为什么您认为您提供了一个值,而实际上您没有提供?您上次 运行 rails 测试是什么时候?谁会从一开始就注意到这一点?
您的模型有 attr_accessor 的名称,但您没有在任何地方设置 attr_accessor 的基础名称字段,因此要么删除 attr_accessor 或设置名称字段来自名字 attr_accessor 在 before_save
你真正想做的是删除你所有的 attr_accessor
另外你为什么要混合编码风格?这是一种不好的做法,因为在维护方面,它可能会让跟在你身后的人感到困惑
在您的迁移中
t.boolean :approved, :default => 0, :null => false
真的应该
t.boolean :approved, default: 0, null: false
使其符合 Rails5 编码风格
Rails 5.1
在我的 seeds.rb 文件中我有:
user = User.new(
:email =>'random@myapp.com',
:password =>'xK#986754',
:password_confirmation =>'xK#986754',
:first_name =>'John',
:last_name =>'Smith',
:role => 1
:approved => true
)
user.skip_invitation
user.save
在我的 user.rb 模型中,我有:
class User < ActiveRecord::Base
enum role: [:user, :vip, :admin]
after_initialize :set_default_role, :if => :new_record?
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable
devise :invitable, :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
attr_accessor :email, :password, :first_name, :last_name, :role, :approved
validates :email, uniqueness: true, presence: true
validates :first_name, presence: true
validates :last_name, presence: true
validates :role, presence: true
def set_default_role
self.role ||= :user
end
end
在我的迁移文件中,我有:
class DeviseCreateUsers < ActiveRecord::Migration[5.1]
def change
create_table :users do |t|
t.string :first_name, null: false
t.string :last_name, null: false
t.integer :role, null: false
t.string :email, null: false
## Approved
t.boolean :approved, :default => 0, :null => false
当我尝试 运行 种子文件时,我收到以下错误消息:
ActiveRecord::NotNullViolation: Mysql2::Error: Field 'first_name' doesn't have a default value: INSERT INTO `users` (`approved`, `created_at`, `updated_at`) VALUES (1, '2017-10-23 02:23:36', '2017-10-23 02:23:36')
我显然在使用这个装置gem
有什么想法吗?
删除您的 attr_accessor
行。 attr_accessor
用于声明在 class 中包装实例变量的简单 getter/setter 方法,它不能与要保存到数据库的属性的 Rails 模型一起使用。这实际上意味着所有 attr_accessor
属性仅存在于内存中,您的模型永远不会尝试将它们写入数据库,因此您的错误消息和插入查询中的所有缺失值。
您没有提供名字值,并且您已告诉数据库不允许为空但没有给出默认值。
那么,为什么您认为您提供了一个值,而实际上您没有提供?您上次 运行 rails 测试是什么时候?谁会从一开始就注意到这一点?
您的模型有 attr_accessor 的名称,但您没有在任何地方设置 attr_accessor 的基础名称字段,因此要么删除 attr_accessor 或设置名称字段来自名字 attr_accessor 在 before_save
你真正想做的是删除你所有的 attr_accessor 另外你为什么要混合编码风格?这是一种不好的做法,因为在维护方面,它可能会让跟在你身后的人感到困惑 在您的迁移中
t.boolean :approved, :default => 0, :null => false
真的应该
t.boolean :approved, default: 0, null: false
使其符合 Rails5 编码风格