79 lines
2.7 KiB
Rust
79 lines
2.7 KiB
Rust
use lumbridge_runtime::{
|
|
CommandConfig, PtyOptions, RuntimeActor, RuntimeActorOptions, RuntimeCommand, RuntimeEvent,
|
|
TerminalSize,
|
|
};
|
|
use lumbridge_terminal::{
|
|
KeyModifiers, TerminalDimensions, TerminalEngine, TerminalEngineOptions, TerminalKey,
|
|
TerminalKeyEvent,
|
|
};
|
|
use std::time::{Duration, Instant};
|
|
|
|
const TEST_TIMEOUT: Duration = Duration::from_secs(3);
|
|
|
|
#[test]
|
|
fn actor_terminal_pipeline_accepts_input_resize_and_vt_output() {
|
|
let command = CommandConfig::new("/bin/sh")
|
|
.unwrap()
|
|
.args([
|
|
"-c",
|
|
"printf '\x1b[31mready\x1b[0m\\n'; IFS= read -r line; stty size; printf 'got:%s\\n' \"$line\"",
|
|
]);
|
|
let actor = RuntimeActor::spawn(
|
|
command,
|
|
PtyOptions::default(),
|
|
RuntimeActorOptions::default(),
|
|
)
|
|
.unwrap();
|
|
let dimensions = TerminalDimensions::new(41, 101).unwrap();
|
|
let mut terminal = TerminalEngine::new(TerminalEngineOptions {
|
|
dimensions: TerminalDimensions::default(),
|
|
scrollback_lines: 64,
|
|
});
|
|
assert!(terminal.resize(dimensions));
|
|
actor
|
|
.try_send(RuntimeCommand::Resize(TerminalSize::new(41, 101).unwrap()))
|
|
.unwrap();
|
|
|
|
let text = terminal.encode_key(&TerminalKeyEvent {
|
|
key: TerminalKey::Text("hello-pipeline".into()),
|
|
modifiers: KeyModifiers::default(),
|
|
});
|
|
actor.try_send(RuntimeCommand::Input(text)).unwrap();
|
|
let enter = terminal.encode_key(&TerminalKeyEvent {
|
|
key: TerminalKey::Enter,
|
|
modifiers: KeyModifiers::default(),
|
|
});
|
|
actor.try_send(RuntimeCommand::Input(enter)).unwrap();
|
|
|
|
let deadline = Instant::now() + TEST_TIMEOUT;
|
|
loop {
|
|
let remaining = deadline.saturating_duration_since(Instant::now());
|
|
assert!(!remaining.is_zero(), "timed out waiting for pipeline exit");
|
|
match actor.recv_timeout(remaining).unwrap() {
|
|
RuntimeEvent::Output { bytes, .. } => {
|
|
let update = terminal.process(&bytes);
|
|
for response in update.outbound {
|
|
actor.try_send(RuntimeCommand::Input(response)).unwrap();
|
|
}
|
|
}
|
|
RuntimeEvent::Exited { status, .. } => {
|
|
assert!(status.success());
|
|
break;
|
|
}
|
|
RuntimeEvent::Fault { message, .. } => panic!("runtime fault: {message}"),
|
|
RuntimeEvent::Started { .. } | RuntimeEvent::InputClosed { .. } => {}
|
|
}
|
|
}
|
|
|
|
let contents = terminal.snapshot().plain_rows().join("\n");
|
|
assert!(contents.contains("ready"), "missing ready marker");
|
|
assert!(
|
|
contents.contains("41 101"),
|
|
"missing resized PTY dimensions"
|
|
);
|
|
assert!(
|
|
contents.contains("got:hello-pipeline"),
|
|
"missing echoed input"
|
|
);
|
|
}
|