<commit_before>module Dynflow
  module Dispatcher
    class ExecutorDispatcher < Abstract
      def initialize(world)
        @world        = Type! world, World
      end

      def handle_request(envelope)
        match(envelope.message,
              on(Execution) { perform_execution(envelope, envelope.message) },
              on(Event)     { perform_event(envelope, envelope.message) })
      end

      private

      def perform_execution(envelope, execution)
        future = Concurrent::IVar.new.with_observer do |_, plan, reason|
          execution_lock = Coordinator::ExecutionLock.new(@world, execution.execution_plan_id, envelope.sender_id, envelope.request_id)
          if plan && plan.state == :running
            @world.invalidate_execution_lock(execution_lock)
          else
            @world.coordinator.release(execution_lock)
            if reason
              respond(envelope, Failed[reason.message])
            else
              respond(envelope, Done)
            end
          end
        end
        allocate_executor(execution.execution_plan_id, envelope.sender_id, envelope.request_id)
        @world.executor.execute(execution.execution_plan_id, future)
        respond(envelope, Accepted)
      rescue Dynflow::Error => e
        respond(envelope, Failed[e.message])
      end

      def perform_event(envelope, event_request)
        future = Concurrent::IVar.new.with_observer do |_, _, reason|
          if reason
            respond(envelope, Failed[reason.message])
          else
            respond(envelope, Done)
          end
        end
        @world.executor.event(event_request.execution_plan_id, event_request.step_id, event_request.event, future)
      end

      def allocate_executor(execution_plan_id, client_world_id, request_id)
        execution_lock = Coordinator::ExecutionLock.new(@world, execution_plan_id, client_world_id, request_id)
        @world.coordinator.acquire(execution_lock)
      end<commit_msg>Don't create an ivar until we're sure we will get to resolve it<commit_after>module Dynflow
  module Dispatcher
    class ExecutorDispatcher < Abstract
      def initialize(world)
        @world        = Type! world, World
      end

      def handle_request(envelope)
        match(envelope.message,
              on(Execution) { perform_execution(envelope, envelope.message) },
              on(Event)     { perform_event(envelope, envelope.message) })
      end

      private

      def perform_execution(envelope, execution)
        allocate_executor(execution.execution_plan_id, envelope.sender_id, envelope.request_id)
        future = Concurrent::IVar.new.with_observer do |_, plan, reason|
          execution_lock = Coordinator::ExecutionLock.new(@world, execution.execution_plan_id, envelope.sender_id, envelope.request_id)
          if plan && plan.state == :running
            @world.invalidate_execution_lock(execution_lock)
          else
            @world.coordinator.release(execution_lock)
            if reason
              respond(envelope, Failed[reason.message])
            else
              respond(envelope, Done)
            end
          end
        end
        @world.executor.execute(execution.execution_plan_id, future)
        respond(envelope, Accepted)
      rescue Dynflow::Error => e
        respond(envelope, Failed[e.message])
      end

      def perform_event(envelope, event_request)
        future = Concurrent::IVar.new.with_observer do |_, _, reason|
          if reason
            respond(envelope, Failed[reason.message])
          else
            respond(envelope, Done)
          end
        end
        @world.executor.event(event_request.execution_plan_id, event_request.step_id, event_request.event, future)
      end

      def allocate_executor(execution_plan_id, client_world_id, request_id)
        execution_lock = Coordinator::ExecutionLock.new(@world, execution_plan_id, client_world_id, request_id)
        @world.coordinator.acquire(execution_lock)
      end
{'fraction_non_alphanumeric': 0.08058058058058058, 'fraction_numerical': 0.0, 'mean_word_length': 2.5592163846838822, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5991820', 'n_tokens_mistral': 1128, 'n_tokens_neox': 1069, 'n_words': 211}