Class: RosettAi::SessionHooks::Installer

Inherits:
Object
  • Object
show all
Defined in:
lib/rosett_ai/session_hooks/installer.rb

Overview

Idempotently wires a Ruby script into the Claude Code settings.json SessionStart and PostToolUse hook sections.

The installer reads the settings file, appends a new hook block if the target command is not already present, and atomically writes the result. A second install call is a no-op.

Examples:

installer = RosettAi::SessionHooks::Installer.new(
  script_path: '/path/to/write_heartbeat.rb'
)
result = installer.install
result[:modified_types] #=> ["SessionStart", "PostToolUse"]

Author:

  • hugo

  • claude

Constant Summary collapse

SETTINGS_PATH =

Default path to the global Claude Code settings file.

File.expand_path('~/.claude/settings.json').freeze
HOOK_TYPES =

Hook event types that receive the heartbeat hook.

['SessionStart', 'PostToolUse'].freeze

Instance Method Summary collapse

Constructor Details

#initialize(script_path:, timeout: 5, settings_path: SETTINGS_PATH) ⇒ Installer

Returns a new instance of Installer.

Parameters:

  • script_path (String)

    absolute path to the Ruby hook script

  • timeout (Integer) (defaults to: 5)

    hook timeout in seconds

  • settings_path (String) (defaults to: SETTINGS_PATH)

    path to settings.json (injectable for tests)



37
38
39
40
41
# File 'lib/rosett_ai/session_hooks/installer.rb', line 37

def initialize(script_path:, timeout: 5, settings_path: SETTINGS_PATH)
  @script_path  = script_path.to_s
  @timeout      = Integer(timeout)
  @settings_path = settings_path.to_s
end

Instance Method Details

#installHash

Install the hook into SessionStart and PostToolUse if not already present.

Returns:

  • (Hash)

    result with keys :modified_types and :already_present_types

Raises:



47
48
49
50
51
52
# File 'lib/rosett_ai/session_hooks/installer.rb', line 47

def install
  settings = load_settings
  modified, already_present = classify_hooks(settings)
  write_settings(settings) unless modified.empty?
  { modified_types: modified, already_present_types: already_present }
end

#installed?Boolean

Check whether the hook is present in all required event types.

Returns:

  • (Boolean)


57
58
59
60
# File 'lib/rosett_ai/session_hooks/installer.rb', line 57

def installed?
  settings = load_settings
  HOOK_TYPES.all? { |ht| hook_present?(settings, ht) }
end