Class: Ace::Review::Molecules::MultiModelExecutor

Inherits:
Object
  • Object
show all
Defined in:
lib/ace/review/molecules/multi_model_executor.rb

Overview

Executes LLM queries concurrently across multiple models Uses Thread-based parallelism with configurable concurrency limit

Constant Summary collapse

DEFAULT_LLM_TIMEOUT =

Default timeout for LLM queries (5 minutes)

300
PROMPT_SIZE_WARNING_THRESHOLD =

Warning threshold: 80% of typical 1M context window

800_000

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(max_concurrent: nil, llm_timeout: nil) ⇒ MultiModelExecutor

Returns a new instance of MultiModelExecutor.



20
21
22
23
24
25
26
27
28
29
30
# File 'lib/ace/review/molecules/multi_model_executor.rb', line 20

def initialize(max_concurrent: nil, llm_timeout: nil)
  # Read from config, fallback to default of 3, clamp to minimum 1
  @max_concurrent = [
    max_concurrent || Ace::Review.get("defaults", "max_concurrent_models") || 3,
    1
  ].max
  # Timeout for LLM queries (in seconds)
  @llm_timeout = llm_timeout || Ace::Review.get("defaults", "llm_timeout") || DEFAULT_LLM_TIMEOUT
  @llm_executor = LlmExecutor.new
  @mutex = Mutex.new
end

Instance Attribute Details

#llm_timeoutObject (readonly)

Returns the value of attribute llm_timeout.



12
13
14
# File 'lib/ace/review/molecules/multi_model_executor.rb', line 12

def llm_timeout
  @llm_timeout
end

#max_concurrentObject (readonly)

Returns the value of attribute max_concurrent.



12
13
14
# File 'lib/ace/review/molecules/multi_model_executor.rb', line 12

def max_concurrent
  @max_concurrent
end

Instance Method Details

#execute(models:, system_prompt:, user_prompt:, session_dir:) ⇒ Hash

Execute reviews concurrently across multiple models

Parameters:

  • models (Array<String>)

    array of model identifiers

  • system_prompt (String)

    system prompt

  • user_prompt (String)

    user prompt

  • session_dir (String)

    session directory for output

Returns:

  • (Hash)

    results hash with per-model outcomes and summary



38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/ace/review/molecules/multi_model_executor.rb', line 38

def execute(models:, system_prompt:, user_prompt:, session_dir:)
  start_time = Time.now
  results = {}

  # Warn once before executing any models
  warn_if_prompt_large(system_prompt, user_prompt, models)

  # Display execution header
  display_header(models)

  # Process models in batches to respect concurrency limit
  models.each_slice(@max_concurrent) do |batch|
    batch_results = execute_batch(batch, system_prompt, user_prompt, session_dir)
    results.merge!(batch_results)
  end

  # Compute summary metrics
  total_duration = Time.now - start_time
  success_count = results.values.count { |r| r[:success] }
  failure_count = results.values.count { |r| !r[:success] }

  {
    success: success_count > 0,
    results: results,
    summary: {
      total_models: models.size,
      success_count: success_count,
      failure_count: failure_count,
      total_duration: total_duration.round(2)
    }
  }
end