#Dunlop::WorkflowStepsInBatchFinished.define do
#  the_final_states_are %w[rejected completed]

#  on_finishing_of :owner_service_window1_preparation do
#    description "Send notification mail to WBA" do |workflow_instance_batch|
#      KpnCoreDeliveryMailer.wba_notification(workflow_instance_batch.id, self.model_name.human).deliver_later
#    end
#  end

#  on_finishing_of :contractor_service_window1_execution do
#    description <<-DESCRIPTION
#      Check ${attributes.owner_service_window2_preparation.migration_file_for_bvt_ready}
#      for ${models.owner_service_window2_preparation} workflow steps in the batch
#    DESCRIPTION
#    action do |workflow_instance_batch|
#      workflow_steps_in_batch_scope(:owner_service_window2_preparation).update_all migration_file_for_bvt_ready: true
#    end

#    description "Send an email to Core Delivery informing them of batch completion" do |workflow_instance_batch|
#      KpnCoreDeliveryMailer.contractor_service_window1_handled_for_batch(workflow_instance_batch.id).deliver_later
#    end

#    description "Send an email to Schuuring informing them of batch completion" do |workflow_instance_batch|
#      SchuuringMailer.workflow_instance_batch_workflow_step_finished(self.class.name, workflow_instance_batch.id).deliver_later
#    end
#  end

#end
module Dunlop::WorkflowStepsInBatchFinished
  @registry = {}
  @final_states = %w[completed rejected]

  def self.registry
    @registry
  end

  def self.final_states
    @final_states
  end

  def self.final_states=(states)
    @final_states = states
  end

  def self.define(&block)
    definition_proxy = DefinitionProxy.new
    definition_proxy.instance_eval(&block)
  end

  def self.handle_workflow_step(workflow_instance_batch, workflow_step)
    return unless definition_proxy = registry[workflow_step.process_name.to_sym]
    batch_states = workflow_step.workflow_steps_in_batch_scope.uniq.pluck(:state)
    #return unless workflow_step.changes[:state].present?
    if batch_states.any? and (batch_states - final_states).empty?
      definition_proxy.actions.each do |action_definition|
        workflow_step.instance_exec(workflow_instance_batch, &action_definition.action)
      end
    end
  end

  class DefinitionProxy
    def on_finishing_of(workflow_step, options = {}, &block)
      workflow_step_proxy = WorkflowStepProxy.new
      workflow_step_proxy.instance_eval(&block)
      Dunlop::WorkflowStepsInBatchFinished.registry[workflow_step] = workflow_step_proxy
    end

    def the_final_states_are(states)
      Dunlop::WorkflowStepsInBatchFinished.final_states = states
    end
  end

  class WorkflowStepProxy
    attr_reader :actions
    def initialize
      @actions = []
      @action_descriptions = []
      @scenarios_definition = nil
    end

    # Actions should be given a discription. This can be done by giving a
    #   description "Hi there, my function is to describe what the following action will do"
    # followed by an
    #   action { do_something }
    # statement. The action can also be added directly on the description by supplying the
    # action Proc:
    #   description "This description will be the action at the same time", scenarios: [:scenario1] do
    #     do_something
    #   end
    def description(description, options = {}, &block)
      @action_descriptions << description
      if block.present? # Action direct specified on description
        action(options, &block)
      end
    end

    def action(options = {}, &block)
      @actions << WorkflowStepAction.new(action: block, descriptions: @action_descriptions.map(&:strip_heredoc), scenarios_definition: @scenarios_definition)
      @action_descriptions = []
    end

    # Allow setting another scope for scenarios
    def scenarios(*scenarios_definition, &block)
      @previous_scenarios_definition = @scenarios_definition
      @scenarios_definition = scenarios_definition
      instance_eval(&block)
      @scenarios_definition = @previous_scenarios_definition
    end
  end

  class WorkflowStepAction
    attr_reader :settings
    def initialize(settings)
      @settings = settings
    end

    def action
      @settings[:action]
    end

    def descriptions
      @settings[:descriptions] || []
    end
  end
end
#require_dependency Rails.root.join("config/initializers/workflow_steps_in_batch_finished_config")
