diff --git a/app/models/runner.rb b/app/models/runner.rb index 4931db8e..21af9d96 100644 --- a/app/models/runner.rb +++ b/app/models/runner.rb @@ -11,10 +11,12 @@ class Runner < ApplicationRecord attr_accessor :strategy def self.strategy_class - @strategy_class ||= begin - strategy_name = CodeOcean::Config.new(:code_ocean).read[:runner_management][:strategy] - "runner/strategy/#{strategy_name}".camelize.constantize - end + @strategy_class ||= if Runner.management_active? + strategy_name = CodeOcean::Config.new(:code_ocean).read[:runner_management][:strategy] + "runner/strategy/#{strategy_name}".camelize.constantize + else + Runner::Strategy::Null + end end def self.management_active? diff --git a/lib/runner/strategy/null.rb b/lib/runner/strategy/null.rb new file mode 100644 index 00000000..38ff522f --- /dev/null +++ b/lib/runner/strategy/null.rb @@ -0,0 +1,57 @@ +# frozen_string_literal: true + +# This strategy allows normal operation of CodeOcean even when the runner management is disabled. +# However, as no command can be executed, all execution requests will fail. +class Runner::Strategy::Null < Runner::Strategy + def self.initialize_environment; end + + def self.sync_environment(_environment); end + + def self.request_from_management(_environment) + SecureRandom.uuid + end + + def destroy_at_management; end + + def copy_files(_files); end + + def attach_to_execution(command, event_loop) + socket = Connection.new(nil, self, event_loop) + # We don't want to return an error if the execution environment is changed + socket.status = :terminated_by_codeocean if command == ExecutionEnvironment::VALIDATION_COMMAND + yield(socket) + socket + end + + def self.available_images + [] + end + + def self.config; end + + def self.release + 'N/A' + end + + def self.pool_size + {} + end + + def self.websocket_header + {} + end + + class Connection < Runner::Connection + def decode(event_data) + event_data + end + + def encode(data) + data + end + + def active? + false + end + end +end