回答:
マイグレーションでそれを行う場合、おそらく次のようにすることができます。
# Make sure no null value exist
MyModel.where(date_column: nil).update_all(date_column: Time.now)
# Change the column to not allow null
change_column :my_models, :date_column, :datetime, null: false
change
(1)ための方法をので、この場合には適していないupdate_all
方法で移動し、潜在的な復帰の両方で実行されます。これは最悪のことではないかもしれませんが、(2)移行では、復帰時に列がどのように変更されたかを知る方法がないためです。したがって、この場合のために、私はに固執するだろうup
とdown
。
Rails 4では、これはより優れた(DRYer)ソリューションです。
change_column_null :my_models, :date_column, false
NULL
その列に値を持つレコードが存在しないことを確認するには、4番目のパラメーターを渡すことができます。これは、値を持つレコードに使用するデフォルト値NULL
です。
change_column_null :my_models, :date_column, false, Time.now
change_column_null
。しかし、上記のリック・スミスのコメントは非常に有効なケースを指摘しています。
Rails 4(他のRails 4の回答には問題があります):
def change
change_column_null(:users, :admin, false, <put a default value here> )
# change_column(:users, :admin, :string, :default => "")
end
NULLを許可しないようにNULL値を含む列を変更すると、問題が発生します。これはまさに、開発セットアップで正常に機能し、LIVEプロダクションにデプロイしようとするとクラッシュするタイプのコードです。最初にNULL値を有効な値に変更してから、NULL を禁止する必要があります。の4番目の値change_column_null
は、まさにそれを行います。詳細については、ドキュメントを参照してください。
また、新しいオブジェクトを作成するたびにフィールドの値を指定する必要がないように、通常はフィールドにデフォルト値を設定することを好みます。それを行うためにコメントアウトしたコードも含めました。
add_column :users, :admin, :string
次にchange_column_null(:admin, :string, false, "new_value_for_existing_records")
値を持つchange_column
ステートメントを持つマイグレーションを作成し:default =>
ます。
change_column :my_table, :my_column, :integer, :default => 0, :null => false
データベースエンジンによっては、使用する必要がある場合があります change_column_null
change_column_null
。
Rails 4:
def change
change_column_null(:users, :admin, false )
end
既存のレコードがある場合は、add_timestampsとnull:falseを使用できないため、解決策は次のとおりです。
def change
add_timestamps(:buttons, null: true)
Button.find_each { |b| b.update(created_at: Time.zone.now, updated_at: Time.zone.now) }
change_column_null(:buttons, :created_at, false)
change_column_null(:buttons, :updated_at, false)
end
MyModel.update_all({:date_column => Time.now}, {:date_column => nil})
。元のフォームのクエリでは、すべてのモデルにフィールドの値がありません。