0

I've got a portfolio model with following fields:

name: string (required)
status: string (required) one of: draft, active, funded

One of the requirement is that a newly created portfolio should have a status draft. I could set a default value inside of migration something like:

create_table :portfolios do |t|
  t.string :name, null: false
  t.string :status, null: false, default: 'draft'

  t.timestamps
end

But I don't think it will easy to maintain. Of course I could set this status inside create method like:

Portfolio.create!(
  name: params[:name],
  status: 'draft'
)

Is there a better way to create such record? maybe some method inside of model?

mr_muscle
  • 2,536
  • 18
  • 61
  • 2
    This might be better as an enum field. See https://stackoverflow.com/a/63018877/2981429 – max pleaner Feb 23 '21 at 00:11
  • Damn, don't now why but after `rails new test_app --skip-test --database=postgresql` it creates me rails with `6.0.3.5` instead. If only I knew I would use 6.1 – mr_muscle Feb 23 '21 at 00:16
  • see [this answer](https://stackoverflow.com/a/1551430/3548935) – Aryeh Beitz Feb 23 '21 at 00:41
  • after_saved callback will do, or any callback which is called after create data – WALVISK Feb 23 '21 at 03:33
  • 1
    Setting the default column value is the way to go. It is not difficult to maintain. ActiveRecord is smart about it too and uses it as the default value when instantiating an instance of that model, so `Portfolio.new.status => 'draft'` – Scott Jacobsen Feb 23 '21 at 04:46
  • This looks like an apt scenario for using a state machine. You can use something like https://github.com/aasm/aasm which lets you define default states and valid transitions – Anuj Feb 23 '21 at 07:05

1 Answers1

1
class Portfolio < ApplicationRecord
  after_initialize do
    self.name = "draft"
  end
end 

I think it's better to do it using after_initialize because this callback will guarantee that the default value will be there from the very beginning of the life cycle of the object

Portfolio.new.name
#shoudl give you draft
M.Elkady
  • 1,093
  • 7
  • 13