diff options
| author | Can Celik <ogulcancelik@gmail.com> | 2026-09-02 14:24:33 +0300 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2026-09-02 14:24:33 +0300 |
| commit | 6c0bb273d5d5405a00985621b17e36f8b4d64609 (patch) | |
| tree | ceef5ea8adf337bf3c1e977b133e76cb763c6f1b /tests | |
| parent | cc88b3b8e5bb9f7d9f23ed6ae85a52fd7b5b9ed6 (diff) | |
feat: support independent multi-client tab views (#3526)
Diffstat (limited to 'tests')
| -rw-r--r-- | tests/multi_client.rs | 53 | ||||
| -rw-r--r-- | tests/support/mod.rs | 12 |
2 files changed, 48 insertions, 17 deletions
diff --git a/tests/multi_client.rs b/tests/multi_client.rs index ae642a22..514493cb 100644 --- a/tests/multi_client.rs +++ b/tests/multi_client.rs @@ -14,7 +14,7 @@ use portable_pty::{native_pty_system, Child, CommandBuilder, MasterPty, PtySize} use serde_json::Value; use support::{ cleanup_test_base, client_shell_handshake, drain_messages, register_runtime_dir, - register_spawned_herdr_pid, send_detach, unregister_spawned_herdr_pid, + register_spawned_herdr_pid, send_client_shell_focus, send_detach, unregister_spawned_herdr_pid, wait_for_client_shell_bootstrap, wait_for_message_variant, wait_for_message_variants, CURRENT_ENDPOINT_PROTOCOL_GENERATION as CURRENT_PROTOCOL, SERVER_MESSAGE_PANE_SURFACE, SERVER_MESSAGE_PANE_SURFACE_PATCH, @@ -252,8 +252,29 @@ fn tty_size(socket: &Path, pane: &str, timeout: Duration) -> (u16, u16) { panic!("pane did not report tty size: {}", pane_text(socket, pane)); } +fn wait_for_tty_size( + socket: &Path, + pane: &str, + timeout: Duration, + expected: impl Fn((u16, u16)) -> bool, +) -> (u16, u16) { + let deadline = Instant::now() + timeout; + loop { + let size = tty_size( + socket, + pane, + deadline.saturating_duration_since(Instant::now()), + ); + if expected(size) { + return size; + } + assert!(Instant::now() < deadline, "unexpected tty size: {size:?}"); + thread::sleep(Duration::from_millis(50)); + } +} + #[test] -fn effective_size_uses_smallest_foreground_client_and_recovers_on_disconnect() { +fn same_tab_geometry_follows_meaningful_client_activity() { let _lock = test_lock(); let base = unique_test_dir(); let config = base.join("config"); @@ -264,26 +285,24 @@ fn effective_size_uses_smallest_foreground_client_and_recovers_on_disconnect() { wait_for_socket(&api, Duration::from_secs(10)); wait_for_file(&clients, Duration::from_secs(10)); let pane = create_pane(&api, "effective-size"); - let mut large = shell(&clients, 120, 40); + let _large = shell(&clients, 120, 40); let mut small = shell(&clients, 80, 24); - let reduced = tty_size(&api, &pane, Duration::from_secs(5)); + let initial = tty_size(&api, &pane, Duration::from_secs(5)); assert!( - reduced.0 <= 24 && reduced.1 <= 80, - "small ClientShell should determine effective size: {reduced:?}" + initial.0 > 24 && initial.1 > 80, + "a passive second connection must not steal geometry: {initial:?}" ); + + send_client_shell_focus(&mut small, true).unwrap(); + let reduced = wait_for_tty_size(&api, &pane, Duration::from_secs(5), |(rows, cols)| { + rows <= 24 && cols <= 80 + }); + send_detach(&mut small).unwrap(); drop(small); - assert!(wait_for_message_variant( - &mut large, - Duration::from_secs(3), - SERVER_MESSAGE_PANE_SURFACE - ) - .unwrap()); - let restored = tty_size(&api, &pane, Duration::from_secs(5)); - assert!( - restored.0 > reduced.0 && restored.1 > reduced.1, - "size should recover: {reduced:?} -> {restored:?}" - ); + wait_for_tty_size(&api, &pane, Duration::from_secs(5), |(rows, cols)| { + rows > reduced.0 && cols > reduced.1 + }); cleanup(server, base); } diff --git a/tests/support/mod.rs b/tests/support/mod.rs index 68337ade..b2dae4be 100644 --- a/tests/support/mod.rs +++ b/tests/support/mod.rs @@ -21,6 +21,7 @@ pub const SERVER_MESSAGE_PANE_SURFACE: u32 = 13; pub const SERVER_MESSAGE_SEMANTIC_NOTIFICATION: u32 = 14; pub const SERVER_MESSAGE_PANE_SURFACE_PATCH: u32 = 19; const CLIENT_MESSAGE_CLIENT_SHELL_PANE_INPUT: u32 = 13; +const CLIENT_MESSAGE_CLIENT_SHELL_FOCUS: u32 = 18; const CLIENT_MESSAGE_ENDPOINT_CONTROL: u32 = 20; pub fn register_spawned_herdr_pid(pid: Option<u32>) { @@ -387,6 +388,17 @@ pub fn send_client_shell_shift_enter(stream: &mut UnixStream, pane_id: &str) -> .map_err(|e| format!("flush client shell key: {e}")) } +pub fn send_client_shell_focus(stream: &mut UnixStream, focused: bool) -> Result<(), String> { + let mut payload = encode_varint_u32(CLIENT_MESSAGE_CLIENT_SHELL_FOCUS); + payload.push(u8::from(focused)); + stream + .write_all(&frame_message(&payload)) + .map_err(|e| format!("write client shell focus: {e}"))?; + stream + .flush() + .map_err(|e| format!("flush client shell focus: {e}")) +} + pub fn send_detach(stream: &mut UnixStream) -> Result<(), String> { let detach_payload = encode_varint_u32(4); let framed = frame_message(&detach_payload); |
