Class: Ralph::Agents::Base

Inherits:
Object
  • Object
show all
Includes:
Helpers
Defined in:
lib/ralph/agents/base.rb

Direct Known Subclasses

ClaudeCode, Codex, OpenCode

Defined Under Namespace

Classes: ExecutionResult

Instance Method Summary collapse

Methods included from Helpers

#check_completion, #escape_regex, #format_duration, #format_duration_long, #format_tool_summary, #now_ms, #strip_ansi, #which

Instance Method Details

#build_args(_prompt, _model, _options) ⇒ Object

Raises:

  • (NotImplementedError)


22
# File 'lib/ralph/agents/base.rb', line 22

def build_args(_prompt, _model, _options) = raise NotImplementedError

#build_env(_options) ⇒ Object



24
# File 'lib/ralph/agents/base.rb', line 24

def build_env(_options) = ENV.to_h.dup

#collect_tool_counts(text) ⇒ Object

Collects tool usage counts from output text. Delegates to parse_tool_output for each line.



48
49
50
51
52
53
54
55
# File 'lib/ralph/agents/base.rb', line 48

def collect_tool_counts(text)
  Hash.new(0).tap do |counts|
    text.each_line do |line|
      tool = parse_tool_output(line)
      counts[tool] += 1 if tool
    end
  end
end

#commandObject

Raises:

  • (NotImplementedError)


18
# File 'lib/ralph/agents/base.rb', line 18

def command     = raise NotImplementedError

#config_nameObject

Raises:

  • (NotImplementedError)


19
# File 'lib/ralph/agents/base.rb', line 19

def config_name = raise NotImplementedError

#detect_fatal_error(_output) ⇒ Object

Returns a fatal error message if one is detected in the output, or nil if no fatal error is found. Subclasses may override.



59
# File 'lib/ralph/agents/base.rb', line 59

def detect_fatal_error(_output) = nil

#execute(prompt, options = {}) ⇒ Object



26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
# File 'lib/ralph/agents/base.rb', line 26

def execute(prompt, options = {})
  command_args = build_args(prompt, options[:model],
                            { allow_all_permissions: options[:allow_all_permissions] })
  environment = build_env(
    filter_plugins: options[:disable_plugins],
    allow_all_permissions: options[:allow_all_permissions]
  )
  full_command = [command] + command_args

  if options[:stream_output]
    execute_streaming(environment, full_command, options[:on_line])
  else
    execute_captured(environment, full_command)
  end
rescue StandardError => agent_error
  Agents::Base::ExecutionResult.new(
    stdout_text: "", stderr_text: agent_error.to_s, tool_counts: {}, exit_code: -1
  )
end

#extract_errors(output) ⇒ Object

Extracts error patterns from agent output. Subclasses may override for agent-specific error formats.



63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
# File 'lib/ralph/agents/base.rb', line 63

def extract_errors(output)
  errors = []
  output.each_line do |line|
    lower = line.downcase
    if lower.include?("error:") ||
       lower.include?("failed:") ||
       lower.include?("exception:") ||
       lower.include?("typeerror") ||
       lower.include?("syntaxerror") ||
       lower.include?("referenceerror") ||
       (lower.include?("test") && lower.include?("fail"))
      cleaned = line.strip[0, 200]
      errors << cleaned if cleaned && !cleaned.empty? && !errors.include?(cleaned)
    end
  end
  errors.first(10)
end

#parse_tool_output(_line) ⇒ Object

Raises:

  • (NotImplementedError)


21
# File 'lib/ralph/agents/base.rb', line 21

def parse_tool_output(_line) = raise NotImplementedError

#typeObject

Raises:

  • (NotImplementedError)


17
# File 'lib/ralph/agents/base.rb', line 17

def type        = raise NotImplementedError

#validate!Object



81
82
83
84
85
86
87
# File 'lib/ralph/agents/base.rb', line 81

def validate!
  path = which(command)
  unless path
    $stderr.puts "Error: #{config_name} CLI ('#{command}') not found."
    exit 1
  end
end