Skip all state machine checks

I am trying to figure out how to skip checks for a specific instance of an ActiveRecord when my backup model goes to a state machine using the rake command. I would like to skip all the checks whenever booking.close! called. Hope to call something like reserve.close! (: Validate => false). FYI we use https://github.com/pluginaweek/state_machine for the state machine.

Here is an example of my booking model.

class Reservation < ActiveRecord::Base validates :ride_id, :start_at, :end_at, presence: true validate :proper_custom_price?, allow_nil: true, on: :update validate :dates_valid? validate :dates_make_sense? scope :needs_close_transition, lambda { where("end_at < ?", Time.now).where("state" => ["requested", "negotiating", "approved"]) } state_machine :initial => 'requested' do all_prebooked = ["requested", "negotiating", "approved"] event :close do transition :from => all_prebooked, :to => "precanceled" end before_transition :on => [:close] do |reservation| reservation.cancel_reason = :admin end end end 

Here is an example of my rake task.

 namespace :reservation do task :close => :environment do puts "== close" Reservation.needs_close_transition.each do |reservation| puts "===> #{reservation.id}" begin reservation.close!(:validate => false) rescue Exception => e Airbrake.notify(e, error_message: e.message) if defined?(Airbrake) end end end 
+5
source share
2 answers

When using the state_machine gemstone, the state attribute is updated before the check runs, so you can add a check condition that checks the current state:

 validates :start_at, :end_at, presence: true, unless: Proc.new {state == 'closed'} 

If you need more complex logic, pass the name of the symbox method to unless instead of proc:

 validates :start_at, :end_at, presence: true, unless: :requires_validation? def requires_validation? # complex logic to determine if the record should be validated end 
+4
source

I had the same problem, however, I did not want to change the current checks, so I checked the state machine code (version 1.2.0) and I found another solution, for your specific case it will be something like:

 reservation.close!(false) reservation.save(validate: false) 

This will call all the callbacks that you defined on your destination computer, and this solution works well for me.

+4
source

Source: https://habr.com/ru/post/1200878/


All Articles