Module: RatatuiRuby::TestHelper::EventInjection
- Included in:
- RatatuiRuby::TestHelper
- Defined in:
- lib/ratatui_ruby/test_helper/event_injection.rb
Overview
Event injection helpers for testing TUI interactions.
Testing keyboard navigation and mouse clicks requires simulating user input. Constructing event objects by hand for every test is verbose and repetitive.
This mixin provides convenience methods to inject keys, clicks, and other events into the test terminal’s event queue. Events are consumed by the next poll_event call.
Use it to simulate user interactions: typing, clicking, dragging, pasting.
Examples
– SPDX-SnippetBegin SPDX-FileCopyrightText: 2026 Kerrick Long SPDX-License-Identifier: MIT-0 ++
with_test_terminal do
inject_keys("h", "e", "l", "l", "o")
inject_keys(:enter, :ctrl_s)
inject_click(x: 10, y: 5)
inject_event(RatatuiRuby::Event::Paste.new(content: "pasted text"))
@app.run
end
– SPDX-SnippetEnd ++
Instance Method Summary collapse
-
#inject_click(x:, y:, modifiers: []) ⇒ Object
Injects a left mouse click.
-
#inject_drag(x:, y:, modifiers: [], button: :left) ⇒ Object
Injects a mouse drag event.
-
#inject_event(event) ⇒ Object
Injects an event into the test terminal’s event queue.
-
#inject_keys(*args) ⇒ Object
(also: #inject_key)
Injects one or more key events.
-
#inject_mouse(x:, y:, kind: :down, modifiers: [], button: :left) ⇒ Object
Injects a mouse event.
-
#inject_right_click(x:, y:, modifiers: []) ⇒ Object
Injects a right mouse click.
-
#inject_sync ⇒ Object
Injects a Sync event.
Instance Method Details
#inject_click(x:, y:, modifiers: []) ⇒ Object
Injects a left mouse click.
Example
inject_click(x: 10, y: 5)
141 142 143 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 141 def inject_click(x:, y:, modifiers: []) inject_mouse(x:, y:, kind: :down, modifiers:, button: :left) end |
#inject_drag(x:, y:, modifiers: [], button: :left) ⇒ Object
Injects a mouse drag event.
Example
inject_drag(x: 10, y: 5)
161 162 163 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 161 def inject_drag(x:, y:, modifiers: [], button: :left) inject_mouse(x:, y:, kind: :drag, modifiers:, button:) end |
#inject_event(event) ⇒ Object
Injects an event into the test terminal’s event queue.
Pass any RatatuiRuby::Event object. The event is returned by the next poll_event call.
Raises RuntimeError if called outside a with_test_terminal block.
Examples
– SPDX-SnippetBegin SPDX-FileCopyrightText: 2026 Kerrick Long SPDX-License-Identifier: MIT-0 ++
inject_event(RatatuiRuby::Event::Key.new(code: "q"))
inject_event(RatatuiRuby::Event::Mouse.new(kind: "down", button: "left", x: 10, y: 5))
inject_event(RatatuiRuby::Event::Paste.new(content: "Hello"))
– SPDX-SnippetEnd ++
- event
-
A
RatatuiRuby::Eventobject.
65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 65 def inject_event(event) unless @_ratatui_test_terminal_active raise RatatuiRuby::Error::Invariant, "Events must be injected inside a `with_test_terminal` block. " \ "Calling this method outside the block causes a race condition where the event " \ "is flushed before the application starts." end case event when RatatuiRuby::Event::Key RatatuiRuby.inject_test_event("key", { code: event.code, modifiers: event.modifiers }) when RatatuiRuby::Event::Mouse RatatuiRuby.inject_test_event("mouse", { kind: event.kind, button: event., x: event.x, y: event.y, modifiers: event.modifiers, }) when RatatuiRuby::Event::Resize RatatuiRuby.inject_test_event("resize", { width: event.width, height: event.height }) when RatatuiRuby::Event::Paste RatatuiRuby.inject_test_event("paste", { content: event.content }) when RatatuiRuby::Event::FocusGained RatatuiRuby.inject_test_event("focus_gained", {}) when RatatuiRuby::Event::FocusLost RatatuiRuby.inject_test_event("focus_lost", {}) when RatatuiRuby::Event::Sync if RatatuiRuby::SyntheticEvents.inline_sync? # Route through native queue for deterministic ordering with key events RatatuiRuby.inject_test_event("sync", {}) else # Default 1.0 behavior: use the engine-level synthetic queue RatatuiRuby::SyntheticEvents.push(event) end else raise ArgumentError, "Unknown event type: #{event.class}" end end |
#inject_keys(*args) ⇒ Object Also known as: inject_key
Injects one or more key events.
Accepts multiple formats for convenience:
-
String: Character key (e.g.,
"a","q") -
Symbol: Named key or modifier combo (e.g.,
:enter,:ctrl_c) -
Hash: Passed to
Key.new -
Key: Passed directly
Examples
– SPDX-SnippetBegin SPDX-FileCopyrightText: 2026 Kerrick Long SPDX-License-Identifier: MIT-0 ++
inject_keys("a", "b", "c")
inject_keys(:enter, :esc)
inject_keys(:ctrl_c, :alt_shift_left)
inject_keys("j", { code: "k", modifiers: ["ctrl"] })
– SPDX-SnippetEnd ++
188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 188 def inject_keys(*args) args.each do |arg| event = case arg when String RatatuiRuby::Event::Key.new(code: arg) when Symbol parts = arg.to_s.split("_") code = parts.pop modifiers = parts RatatuiRuby::Event::Key.new(code:, modifiers:) when Hash RatatuiRuby::Event::Key.new(**arg) when RatatuiRuby::Event::Key arg else raise ArgumentError, "Invalid key argument: #{arg.inspect}. Expected String, Symbol, Hash, or Key event." end inject_event(event) end end |
#inject_mouse(x:, y:, kind: :down, modifiers: [], button: :left) ⇒ Object
Injects a mouse event.
Example
– SPDX-SnippetBegin SPDX-FileCopyrightText: 2026 Kerrick Long SPDX-License-Identifier: MIT-0 ++
inject_mouse(x: 10, y: 5, kind: :down, button: :left)
– SPDX-SnippetEnd ++
- x
-
Integer x-coordinate.
- y
-
Integer y-coordinate.
- kind
-
Symbol
:down,:up, or:drag. - button
-
Symbol
:left,:right, or:middle. - modifiers
-
Array of modifier strings.
124 125 126 127 128 129 130 131 132 133 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 124 def inject_mouse(x:, y:, kind: :down, modifiers: [], button: :left) event = RatatuiRuby::Event::Mouse.new( kind: kind.to_s, x:, y:, button: .to_s, modifiers: ) inject_event(event) end |
#inject_right_click(x:, y:, modifiers: []) ⇒ Object
Injects a right mouse click.
Example
inject_right_click(x: 10, y: 5)
151 152 153 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 151 def inject_right_click(x:, y:, modifiers: []) inject_mouse(x:, y:, kind: :down, modifiers:, button: :right) end |
#inject_sync ⇒ Object
Injects a Sync event.
When a runtime (Tea, Kit) encounters this event, it should wait for all pending async operations to complete before processing the next event. This enables deterministic testing of async behavior.
Important: Sync waits for commands to complete. Do not use it with long-running commands that wait indefinitely (e.g., for cancellation). Those commands will block forever, causing a timeout. For cancellation tests, dispatch the cancel command without Sync.
Example
– SPDX-SnippetBegin SPDX-FileCopyrightText: 2026 Kerrick Long SPDX-License-Identifier: MIT-0 ++
inject_key("s") # Triggers async command
inject_sync # Wait for command to complete
inject_key(:q) # Quit after seeing results
– SPDX-SnippetEnd ++
236 237 238 |
# File 'lib/ratatui_ruby/test_helper/event_injection.rb', line 236 def inject_sync inject_event(RatatuiRuby::Event::Sync.new) end |