SteppableTerminal

Struct SteppableTerminal 

Source
#[non_exhaustive]
pub struct SteppableTerminal { pub shadow_terminal: ShadowTerminal, pub pty_task_handle: Arc<Mutex<JoinHandle<Result<(), PTYError>>>>, pub pty_input_tx: Sender<BytesFromSTDIN>, }
Expand description

This Steppable Terminal is likely more useful for running end to end tests.

It doesn’t run [ShadowTerminal] in a loop and so requires calling certain methods manually to advance the terminal frontend. It also exposes the underyling [Wezterm] terminal that has a wealth of useful methods for interacting with it.

Fields (Non-exhaustive)§

This struct is marked as non-exhaustive
Non-exhaustive structs could have additional fields added in future. Therefore, non-exhaustive structs cannot be constructed in external crates using the traditional Struct { .. } syntax; cannot be matched against without a wildcard ..; and struct update syntax will not work.
§shadow_terminal: ShadowTerminal

The [ShadowTerminal] frontend combines a PTY process and a [Wezterm] terminal instance.

§pty_task_handle: Arc<Mutex<JoinHandle<Result<(), PTYError>>>>

The underlying PTY’s Tokio task handle.

§pty_input_tx: Sender<BytesFromSTDIN>

A Tokio channel that forwards bytes to the underlying PTY’s STDIN.

Implementations§

Source§

impl SteppableTerminal

Source

pub async fn start(config: Config) -> Result<Self, SteppableTerminalError>

Starts the terminal. Waits for first output before returning.

§Errors

If it doesn’t receive any output in time.

Source

pub fn kill(&self) -> Result<(), SteppableTerminalError>

Broadcast the shutdown signal. This should exit both the underlying PTY process and the main ShadowTerminal loop.

§Errors

If the End messaage could not be sent.

Source

pub fn send_input(&self, input: Input) -> Result<(), PTYError>

Send input directly into the underlying PTY process. This doesn’t go through the shadow terminal’s “frontend”.

For some reason this function is unreliable when sending more than one character. It is better to send larger strings using the OSC Paste mode. See [self.paste_string()]

§Errors

If sending the string fails

Source

pub fn send_command(&self, command: &str) -> Result<(), PTYError>

Send a command to the terminal REPL. This pastes the command body, then sends a single newline to tell the TTY to run the command.

§Errors

If sending the string fails

Source

pub fn send_command_with_osc_paste(&self, command: &str) -> Result<(), PTYError>

Send a command using an OSC paste event.

This is generally the preferred way to send commands. It’s just more efficient then sending each character separately. However, for some reason, that I haven’t been able to get to the bottom of, some PTY processes parse out the OSC paste ANSI codes and some don’t. I didn’t even know that PTY’s had anything to do with parsing ANSI, so I could well be mistaken and would appreciate being corrected.

So if you have problems with this function then just use send_command() instead.

@tombh July 2025.

§Errors

If sending the string fails

Source

pub fn paste_string(&self, string: &str) -> Result<(), PTYError>

Use OSC Paste codes to send a large amount of text at once to the terminal.

§Errors

If sending the string fails

Source

pub async fn render_all_output(&mut self) -> Result<(), PTYError>

Consume all the new output from the underlying PTY and have Wezterm render it in the shadow terminal.

Warning: this function could block if there is no end to the output from the PTY.

§Errors

If PTY output can’t be handled.

Source

pub fn get_scrollback_position( &mut self, ) -> Result<usize, SteppableTerminalError>

Get the position of the top of the screen in the scrollback history.

§Errors

If it can’t convert the position from isize to usize

Source

pub fn screen_as_string(&mut self) -> Result<String, SteppableTerminalError>

Convert the current Wezterm shadow terminal screen to a plain string.

§Errors

If it can’t write into the output string

Source

pub fn get_coords_of_cell_by_content( &mut self, content: &str, ) -> Option<(usize, usize)>

Return the screen coordinates of a matching cell’s contents.

§Errors

If it can’t write into the output string

Source

pub fn get_cell_at( &mut self, x: usize, y: usize, ) -> Result<Option<Cell>, SteppableTerminalError>

Get the wezterm_term::Cell at the given coordinates.

§Errors

If the cell at the given coordinates cannot be fetched.

Source

pub fn get_string_at( &mut self, x: usize, y: usize, length: usize, ) -> Result<String, SteppableTerminalError>

Get the string, of the given length, at the given coordinates.

§Errors

If any of the cells at the given coordinates cannot be fetched.

Source

pub fn dump_screen(&mut self) -> Result<(), SteppableTerminalError>

Prints the contents of the current screen to STDERR

§Errors

If it can’t get the screen output.

Source

pub async fn get_prompt_string( command: Vec<OsString>, ) -> Result<String, SteppableTerminalError>

Get the prompt as a string. Useful for reproducibility as prompts can change between machines.

§Errors
  • If a steppable terminal can’t be created.
  • If the terminal’s screen can’t be parsed.
Source

pub async fn wait_for_any_change( &mut self, ) -> Result<(), SteppableTerminalError>

Wait for the screen to change in any way.

§Errors
  • If it can’t get the screen contents.
  • If no change is found within a certain time.
Source

pub async fn wait_for_string( &mut self, string: &str, maybe_timeout: Option<u32>, ) -> Result<(), SteppableTerminalError>

Wait for the given string to appear anywhere in the screen.

§Errors
  • If it can’t get the screen contents.
  • If no change is found within a certain time.
Source

pub async fn wait_for_string_at( &mut self, string_to_find: &str, x: usize, y: usize, maybe_timeout: Option<u32>, ) -> Result<(), SteppableTerminalError>

Wait for the given string to appear at the given coordinates.

§Errors
  • If it can’t get the screen contents.
  • If no change is found within a certain time.
Source

pub async fn wait_for_bg_color_at( &mut self, maybe_colour: Option<(f32, f32, f32, f32)>, x: usize, y: usize, maybe_timeout: Option<u32>, ) -> Result<(), SteppableTerminalError>

Wait for the given background colour at the given coordinates

§Errors
  • If it can’t get the screen contents.
  • If it no cell is found at the coords
Source

pub async fn wait_for_fg_color_at( &mut self, maybe_colour: Option<(f32, f32, f32, f32)>, x: usize, y: usize, maybe_timeout: Option<u32>, ) -> Result<(), SteppableTerminalError>

Wait for the given foreground colour at the given coordinates

§Errors
  • If it can’t get the screen contents.
  • If it no cell is found at the coords
Source

pub async fn wait_for_colors_at( &mut self, background_colour: Option<(f32, f32, f32, f32)>, foreground_colour: Option<(f32, f32, f32, f32)>, x: usize, y: usize, maybe_timeout: Option<u32>, ) -> Result<(), SteppableTerminalError>

Wait for the given foreground and background colour at the given coordinates

§Errors
  • If it can’t get the screen contents.
  • If it no cell is found at the coords
Source

pub const fn extract_colour( colour_attribute: ColorAttribute, ) -> Option<SrgbaTuple>

Get the colour of a cell from its colour attribute.

Trait Implementations§

Source§

impl Drop for SteppableTerminal

Source§

fn drop(&mut self)

Executes the destructor for this type. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> Downcast for T
where T: Any,

Source§

fn into_any(self: Box<T>) -> Box<dyn Any>

Convert Box<dyn Trait> (where Trait: Downcast) to Box<dyn Any>. Box<dyn Any> can then be further downcast into Box<ConcreteType> where ConcreteType implements Trait.
Source§

fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>

Convert Rc<Trait> (where Trait: Downcast) to Rc<Any>. Rc<Any> can then be further downcast into Rc<ConcreteType> where ConcreteType implements Trait.
Source§

fn as_any(&self) -> &(dyn Any + 'static)

Convert &Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &Any’s vtable from &Trait’s.
Source§

fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)

Convert &mut Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &mut Any’s vtable from &mut Trait’s.
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Pointable for T

Source§

const ALIGN: usize

The alignment of pointer.
Source§

type Init = T

The type for initializers.
Source§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
Source§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
Source§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
Source§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

impl<T> ErasedDestructor for T
where T: 'static,