Class: OKF::Pro::Event
- Inherits:
-
Object
- Object
- OKF::Pro::Event
- Defined in:
- lib/okf/pro/event.rb
Overview
The hook event: the only place this checker parses input it did not write.
An event it cannot read is enforcement that did not run, so the failure is
recorded rather than swallowed. The first cut rescued the parse error into
an empty hash, every guard read an empty path, and the check passed — the
same shape as the jq hole this checker exists to close, rebuilt in Ruby.
Whoever calls it decides what to do with the failure; nobody gets to not
know about it.
Instance Attribute Summary collapse
-
#parse_error ⇒ Object
readonly
Returns the value of attribute parse_error.
Class Method Summary collapse
Instance Method Summary collapse
-
#added_text ⇒ Object
Both spellings are read on purpose.
-
#command ⇒ Object
Bash's payload.
- #cwd ⇒ Object
- #file_path ⇒ Object
-
#initialize(raw) ⇒ Event
constructor
A new instance of Event.
- #parse_error? ⇒ Boolean
- #stop_hook_active? ⇒ Boolean
- #tool_input ⇒ Object
- #tool_name ⇒ Object
Constructor Details
#initialize(raw) ⇒ Event
Returns a new instance of Event.
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 |
# File 'lib/okf/pro/event.rb', line 20 def initialize(raw) @data = {} @parse_error = nil # The same defense Pro.read_text gives files, applied to the one # input that arrives as a stream: forced to UTF-8 and scrubbed. Stdin # under a bare locale (common in CI and git hooks) arrives tagged # US-ASCII, and a clean em dash in an edit's new_string then raised # out of the very first string operation — above the dispatch rescue, # so ruby exited 1, which the hook protocol reads as NON-BLOCKING. # The guard's own input was the bypass. text = raw.to_s.dup.force_encoding(Encoding::UTF_8).scrub if text.strip.empty? @parse_error = "the hook received no event on stdin" return end begin parsed = JSON.parse(text) if parsed.is_a?(Hash) @data = parsed else @parse_error = "the event was #{parsed.class}, not a JSON object" end rescue JSON::ParserError => e @parse_error = "the event was not parseable JSON (#{e..split("\n").first})" end end |
Instance Attribute Details
#parse_error ⇒ Object (readonly)
Returns the value of attribute parse_error.
14 15 16 |
# File 'lib/okf/pro/event.rb', line 14 def parse_error @parse_error end |
Class Method Details
.from_stdin(io = $stdin) ⇒ Object
16 17 18 |
# File 'lib/okf/pro/event.rb', line 16 def self.from_stdin(io = $stdin) new(io.read) end |
Instance Method Details
#added_text ⇒ Object
Both spellings are read on purpose. Claude Code's Edit/MultiEdit send
new_string; the shell shims this replaces only ever looked for
new_str, so the verified: guard passed every real edit it was built
to stop and only ever refused the synthetic JSON in its own drill. A gate
tested exclusively by the shape it was written against is not tested.
85 86 87 88 89 90 91 92 |
# File 'lib/okf/pro/event.rb', line 85 def added_text parts = [ tool_input["new_string"], tool_input["new_str"], tool_input["content"] ] edits = tool_input["edits"] if edits.is_a?(Array) parts.concat(edits.map { |e| e.is_a?(Hash) ? [ e["new_string"], e["new_str"] ] : nil }) end parts.flatten.compact.join("\n") end |
#command ⇒ Object
Bash's payload. Named for what it is rather than reached for through tool_input at three call sites.
71 72 73 |
# File 'lib/okf/pro/event.rb', line 71 def command tool_input["command"].to_s end |
#cwd ⇒ Object
75 76 77 78 |
# File 'lib/okf/pro/event.rb', line 75 def cwd raw = @data["cwd"].to_s raw.empty? ? Dir.pwd : raw end |
#file_path ⇒ Object
65 66 67 |
# File 'lib/okf/pro/event.rb', line 65 def file_path tool_input["file_path"].to_s end |
#parse_error? ⇒ Boolean
49 50 51 |
# File 'lib/okf/pro/event.rb', line 49 def parse_error? !@parse_error.nil? end |
#stop_hook_active? ⇒ Boolean
57 58 59 |
# File 'lib/okf/pro/event.rb', line 57 def stop_hook_active? @data["stop_hook_active"] == true end |
#tool_input ⇒ Object
61 62 63 |
# File 'lib/okf/pro/event.rb', line 61 def tool_input @data["tool_input"].is_a?(Hash) ? @data["tool_input"] : {} end |
#tool_name ⇒ Object
53 54 55 |
# File 'lib/okf/pro/event.rb', line 53 def tool_name @data["tool_name"].to_s end |