diff options
author | Kunal Mohan <kunalmohan99@gmail.com> | 2021-04-16 00:31:08 +0530 |
---|---|---|
committer | Kunal Mohan <kunalmohan99@gmail.com> | 2021-04-16 00:31:08 +0530 |
commit | d0ee751b6c0a6df1f18e1d0f99d9eca1b121ec04 (patch) | |
tree | c8ab41f0d16aaf805365852ff82c4af62045e13c | |
parent | 4f0ed908102f70b60350a33898d424ce3d41230f (diff) |
Refactor ServerInstruction enum to use Action enum
-rw-r--r-- | src/client/mod.rs | 9 | ||||
-rw-r--r-- | src/client/tab.rs | 2 | ||||
-rw-r--r-- | src/common/errors.rs | 12 | ||||
-rw-r--r-- | src/common/input/handler.rs | 123 | ||||
-rw-r--r-- | src/common/pty_bus.rs | 3 | ||||
-rw-r--r-- | src/common/screen.rs | 5 | ||||
-rw-r--r-- | src/server/mod.rs | 303 |
7 files changed, 181 insertions, 276 deletions
diff --git a/src/client/mod.rs b/src/client/mod.rs index 7dc38f5e1..014597363 100644 --- a/src/client/mod.rs +++ b/src/client/mod.rs @@ -24,7 +24,7 @@ use crate::server::ServerInstruction; #[derive(Serialize, Deserialize, Debug, Clone)] pub enum ClientInstruction { Error(String), - Render(String), + Render(Option<String>), DoneClosingPane, DoneOpeningNewPane, DoneUpdatingTabs, @@ -92,7 +92,7 @@ pub fn start_client(mut os_input: Box<dyn ClientOsApi>, opts: CliArgs) { os_input.receive_sigwinch(Box::new({ let os_api = os_input.clone(); move || { - os_api.send_to_server(ServerInstruction::terminal_resize( + os_api.send_to_server(ServerInstruction::TerminalResize( os_api.get_terminal_size_using_fd(0), )); } @@ -148,9 +148,12 @@ pub fn start_client(mut os_input: Box<dyn ClientOsApi>, opts: CliArgs) { std::process::exit(1); } ClientInstruction::Render(output) => { + if output.is_none() { + break; + } let mut stdout = os_input.get_stdout_writer(); stdout - .write_all(&output.as_bytes()) + .write_all(&output.unwrap().as_bytes()) .expect("cannot write to stdout"); stdout.flush().expect("could not flush"); } diff --git a/src/client/tab.rs b/src/client/tab.rs index 1fdad6e2a..9a268d2bd 100644 --- a/src/client/tab.rs +++ b/src/client/tab.rs @@ -727,7 +727,7 @@ impl Tab { } self.send_server_instructions - .send(ServerInstruction::Render(output)) + .send(ServerInstruction::Render(Some(output))) .unwrap(); } fn get_panes(&self) -> impl Iterator<Item = (&PaneId, &Box<dyn Pane>)> { diff --git a/src/common/errors.rs b/src/common/errors.rs index bedc9d7f6..6b609299a 100644 --- a/src/common/errors.rs +++ b/src/common/errors.rs @@ -344,15 +344,13 @@ pub enum ServerContext { SplitVertically, MoveFocus, NewClient, - ToPty, - ToScreen, + Action, Render, - PluginUpdate, + TerminalResize, DoneClosingPane, DoneOpeningNewPane, DoneUpdatingTabs, ClientExit, - ClientShouldExit, Exit, } @@ -364,15 +362,13 @@ impl From<&ServerInstruction> for ServerContext { ServerInstruction::SplitVertically => ServerContext::SplitVertically, ServerInstruction::MoveFocus => ServerContext::MoveFocus, ServerInstruction::NewClient(..) => ServerContext::NewClient, - ServerInstruction::ToPty(_) => ServerContext::ToPty, - ServerInstruction::ToScreen(_) => ServerContext::ToScreen, - ServerInstruction::PluginUpdate(..) => ServerContext::PluginUpdate, + ServerInstruction::Action(_) => ServerContext::Action, + ServerInstruction::TerminalResize(_) => ServerContext::TerminalResize, ServerInstruction::Render(_) => ServerContext::Render, ServerInstruction::DoneClosingPane => ServerContext::DoneClosingPane, ServerInstruction::DoneOpeningNewPane => ServerContext::DoneOpeningNewPane, ServerInstruction::DoneUpdatingTabs => ServerContext::DoneUpdatingTabs, ServerInstruction::ClientExit => ServerContext::ClientExit, - ServerInstruction::ClientShouldExit => ServerContext::ClientShouldExit, ServerInstruction::Exit => ServerContext::Exit, } } diff --git a/src/common/input/handler.rs b/src/common/input/handler.rs index 90df5b6a5..135d05481 100644 --- a/src/common/input/handler.rs +++ b/src/common/input/handler.rs @@ -7,13 +7,11 @@ use crate::common::input::config::Config; use crate::common::{SenderWithContext, OPENCALLS}; use crate::errors::ContextType; use crate::os_input_output::ClientOsApi; -use crate::pty_bus::PtyInstruction; -use crate::screen::ScreenInstruction; use crate::server::ServerInstruction; use crate::CommandIsExecuting; use termion::input::{TermRead, TermReadEventsAndRaw}; -use zellij_tile::data::{Event, InputMode, Key, ModeInfo}; +use zellij_tile::data::{InputMode, Key, ModeInfo}; /// Handles the dispatching of [`Action`]s according to the current /// [`InputMode`], and keep tracks of the current [`InputMode`]. @@ -106,12 +104,6 @@ impl InputHandler { let mut should_break = false; match action { - Action::Write(val) => { - self.os_input - .send_to_server(ServerInstruction::clear_scroll()); - self.os_input - .send_to_server(ServerInstruction::write_character(val)); - } Action::Quit => { self.exit(); should_break = true; @@ -119,120 +111,33 @@ impl InputHandler { Action::SwitchToMode(mode) => { self.mode = mode; self.os_input - .send_to_server(ServerInstruction::PluginUpdate( - None, - Event::ModeUpdate(get_mode_info(mode)), - )); - self.os_input - .send_to_server(ServerInstruction::change_mode(get_mode_info(mode))); - self.os_input.send_to_server(ServerInstruction::render()); - } - Action::Resize(direction) => { - let screen_instr = match direction { - super::actions::Direction::Left => ServerInstruction::resize_left(), - super::actions::Direction::Right => ServerInstruction::resize_right(), - super::actions::Direction::Up => ServerInstruction::resize_up(), - super::actions::Direction::Down => ServerInstruction::resize_down(), - }; - self.os_input.send_to_server(screen_instr); - } - Action::SwitchFocus => { - self.os_input - .send_to_server(ServerInstruction::ToScreen(ScreenInstruction::SwitchFocus)); - } - Action::FocusNextPane => { - self.os_input.send_to_server(ServerInstruction::ToScreen( - ScreenInstruction::FocusNextPane, - )); - } - Action::FocusPreviousPane => { - self.os_input.send_to_server(ServerInstruction::ToScreen( - ScreenInstruction::FocusPreviousPane, - )); + .send_to_server(ServerInstruction::Action(action.clone())); } - Action::MoveFocus(direction) => { - let screen_instr = match direction { - super::actions::Direction::Left => ServerInstruction::move_focus_left(), - super::actions::Direction::Right => ServerInstruction::move_focus_right(), - super::actions::Direction::Up => ServerInstruction::move_focus_up(), - super::actions::Direction::Down => ServerInstruction::move_focus_down(), - }; - self.os_input.send_to_server(screen_instr); - } - Action::ScrollUp => { - self.os_input.send_to_server(ServerInstruction::scroll_up()); - } - Action::ScrollDown => { - self.os_input - .send_to_server(ServerInstruction::scroll_down()); - } - Action::ToggleFocusFullscreen => { - self.os_input - .send_to_server(ServerInstruction::toggle_active_terminal_fullscreen()); - } - Action::NewPane(direction) => { - let pty_instr = match direction { - Some(super::actions::Direction::Left) => { - PtyInstruction::SpawnTerminalVertically(None) - } - Some(super::actions::Direction::Right) => { - PtyInstruction::SpawnTerminalVertically(None) - } - Some(super::actions::Direction::Up) => { - PtyInstruction::SpawnTerminalHorizontally(None) - } - Some(super::actions::Direction::Down) => { - PtyInstruction::SpawnTerminalHorizontally(None) - } - // No direction specified - try to put it in the biggest available spot - None => PtyInstruction::SpawnTerminal(None), - }; + Action::NewPane(_) => { self.command_is_executing.opening_new_pane(); self.os_input - .send_to_server(ServerInstruction::ToPty(pty_instr)); + .send_to_server(ServerInstruction::Action(action)); self.command_is_executing.wait_until_new_pane_is_opened(); } Action::CloseFocus => { self.command_is_executing.closing_pane(); self.os_input - .send_to_server(ServerInstruction::close_focused_pane()); + .send_to_server(ServerInstruction::Action(action)); self.command_is_executing.wait_until_pane_is_closed(); } - Action::NewTab => { + Action::NewTab + | Action::GoToNextTab + | Action::GoToPreviousTab + | Action::CloseTab + | Action::GoToTab(_) => { self.command_is_executing.updating_tabs(); self.os_input - .send_to_server(ServerInstruction::pty_new_tab()); + .send_to_server(ServerInstruction::Action(action)); self.command_is_executing.wait_until_tabs_are_updated(); } - Action::GoToNextTab => { - self.command_is_executing.updating_tabs(); - self.os_input - .send_to_server(ServerInstruction::switch_tab_next()); - self.command_is_executing.wait_until_tabs_are_updated(); - } - Action::GoToPreviousTab => { - self.command_is_executing.updating_tabs(); - self.os_input - .send_to_server(ServerInstruction::switch_tab_prev()); - self.command_is_executing.wait_until_tabs_are_updated(); - } - Action::CloseTab => { - self.command_is_executing.updating_tabs(); - self.os_input - .send_to_server(ServerInstruction::screen_close_tab()); - self.command_is_executing.wait_until_tabs_are_updated(); - } - Action::GoToTab(i) => { - self.command_is_executing.updating_tabs(); - self.os_input - .send_to_server(ServerInstruction::go_to_tab(i)); - self.command_is_executing.wait_until_tabs_are_updated(); - } - Action::TabNameInput(c) => { - self.os_input - .send_to_server(ServerInstruction::update_tab_name(c)); - } - Action::NoOp => {} + _ => self + .os_input + .send_to_server(ServerInstruction::Action(action)), } should_break diff --git a/src/common/pty_bus.rs b/src/common/pty_bus.rs index b8eaba3bd..be7bb1bc5 100644 --- a/src/common/pty_bus.rs +++ b/src/common/pty_bus.rs @@ -6,7 +6,6 @@ use ::std::os::unix::io::RawFd; use ::std::pin::*; use ::std::sync::mpsc::Receiver; use ::std::time::{Duration, Instant}; -use serde::{Deserialize, Serialize}; use std::path::PathBuf; use super::SenderWithContext; @@ -69,7 +68,7 @@ impl Stream for ReadFromPid { pub type VteBytes = Vec<u8>; /// Instructions related to PTYs (pseudoterminals). -#[derive(Clone, Debug, Serialize, Deserialize)] +#[derive(Clone, Debug)] pub enum PtyInstruction { SpawnTerminal(Option<PathBuf>), SpawnTerminalVertically(Option<PathBuf>), diff --git a/src/common/screen.rs b/src/common/screen.rs index e41e042eb..dfd952a7a 100644 --- a/src/common/screen.rs +++ b/src/common/screen.rs @@ -1,6 +1,5 @@ //! Things related to [`Screen`]s. -use serde::{Deserialize, Serialize}; use std::collections::BTreeMap; use std::os::unix::io::RawFd; use std::path::PathBuf; @@ -19,7 +18,7 @@ use crate::{layout::Layout, panes::PaneId}; use zellij_tile::data::{Event, ModeInfo, TabInfo}; /// Instructions that can be sent to the [`Screen`]. -#[derive(Debug, Clone, Serialize, Deserialize)] +#[derive(Debug, Clone)] pub enum ScreenInstruction { PtyBytes(RawFd, VteBytes), Render, @@ -209,7 +208,7 @@ impl Screen { if self.tabs.is_empty() { self.active_tab_index = None; self.send_server_instructions - .send(ServerInstruction::ClientShouldExit) + .send(ServerInstruction::Render(None)) .unwrap(); } else { for t in self.tabs.values_mut() { diff --git a/src/server/mod.rs b/src/server/mod.rs index e5a61f81c..adf3c9b25 100644 --- a/src/server/mod.rs +++ b/src/server/mod.rs @@ -1,6 +1,5 @@ use directories_next::ProjectDirs; use serde::{Deserialize, Serialize}; -use std::os::unix::io::RawFd; use std::path::PathBuf; use std::sync::mpsc::channel; use std::thread; @@ -18,8 +17,10 @@ use crate::cli::CliArgs; use crate::client::ClientInstruction; use crate::common::{ errors::{ContextType, PluginContext, PtyContext, ScreenContext, ServerContext}, + input::actions::{Action, Direction}, + input::handler::get_mode_info, os_input_output::ServerOsApi, - pty_bus::{PtyBus, PtyInstruction, VteBytes}, + pty_bus::{PtyBus, PtyInstruction}, screen::{Screen, ScreenInstruction}, wasm_vm::{wasi_stdout, wasi_write_string, zellij_imports, PluginEnv, PluginInstruction}, ChannelWithContext, SenderType, SenderWithContext, @@ -36,144 +37,17 @@ pub enum ServerInstruction { SplitHorizontally, SplitVertically, MoveFocus, + TerminalResize(PositionAndSize), NewClient(String, PositionAndSize), - ToPty(PtyInstruction), - ToScreen(ScreenInstruction), - Render(String), - PluginUpdate(Option<u32>, Event), + Action(Action), + Render(Option<String>), DoneClosingPane, DoneOpeningNewPane, DoneUpdatingTabs, ClientExit, - ClientShouldExit, // notify router thread to exit Exit, } -impl ServerInstruction { - // ToPty - pub fn spawn_terminal(path: Option<PathBuf>) -> Self { - Self::ToPty(PtyInstruction::SpawnTerminal(path)) - } - pub fn spawn_terminal_vertically(path: Option<PathBuf>) -> Self { - Self::ToPty(PtyInstruction::SpawnTerminalVertically(path)) - } - pub fn spawn_terminal_horizontally(path: Option<PathBuf>) -> Self { - Self::ToPty(PtyInstruction::SpawnTerminalHorizontally(path)) - } - pub fn pty_new_tab() -> Self { - Self::ToPty(PtyInstruction::NewTab) - } - pub fn pty_close_pane(id: PaneId) -> Self { - Self::ToPty(PtyInstruction::ClosePane(id)) - } - pub fn pty_close_tab(ids: Vec<PaneId>) -> Self { - Self::ToPty(PtyInstruction::CloseTab(ids)) - } - pub fn pty_exit() -> Self { - Self::ToPty(PtyInstruction::Exit) - } - - // ToScreen - pub fn render() -> Self { - Self::ToScreen(ScreenInstruction::Render) - } - pub fn new_pane(id: PaneId) -> Self { - Self::ToScreen(ScreenInstruction::NewPane(id)) - } - pub fn horizontal_split(id: PaneId) -> Self { - Self::ToScreen(ScreenInstruction::HorizontalSplit(id)) - } - pub fn vertical_split(id: PaneId) -> Self { - Self::ToScreen(ScreenInstruction::VerticalSplit(id)) - } - pub fn write_character(chars: Vec<u8>) -> Self { - Self::ToScreen(ScreenInstruction::WriteCharacter(chars)) - } - pub fn resize_left() -> Self { - Self::ToScreen(ScreenInstruction::ResizeLeft) - } - pub fn resize_right() -> Self { - Self::ToScreen(ScreenInstruction::ResizeRight) - } - pub fn resize_down() -> Self { - Self::ToScreen(ScreenInstruction::ResizeDown) - } - pub fn resize_up() -> Self { - Self::ToScreen(ScreenInstruction::ResizeUp) - } - pub fn move_focus_left() -> Self { - Self::ToScreen(ScreenInstruction::MoveFocusLeft) - } - pub fn move_focus_right() -> Self { - Self::ToScreen(ScreenInstruction::MoveFocusRight) - } - pub fn move_focus_down() -> Self { - Self::ToScreen(ScreenInstruction::MoveFocusDown) - } - pub fn move_focus_up() -> Self { - Self::ToScreen(ScreenInstruction::MoveFocusUp) - } - pub fn screen_exit() -> Self { - Self::ToScreen(ScreenInstruction::Exit) - } - pub fn scroll_up() -> Self { - Self::ToScreen(ScreenInstruction::ScrollUp) - } - pub fn scroll_down() -> Self { - Self::ToScreen(ScreenInstruction::ScrollDown) - } - pub fn clear_scroll() -> Self { - Self::ToScreen(ScreenInstruction::ClearScroll) - } - pub fn close_focused_pane() -> Self { - Self::ToScreen(ScreenInstruction::CloseFocusedPane) - } - pub fn toggle_active_terminal_fullscreen() -> Self { - Self::ToScreen(ScreenInstruction::ToggleActiveTerminalFullscreen) - } - pub fn set_selectable(pane_id: PaneId, value: bool) -> Self { - Self::ToScreen(ScreenInstruction::SetSelectable(pane_id, value)) - } - pub fn set_max_height(pane_id: PaneId, max_height: usize) -> Self { - Self::ToScreen(ScreenInstruction::SetMaxHeight(pane_id, max_height)) - } - pub fn set_invisible_borders(pane_id: PaneId, value: bool) -> Self { - Self::ToScreen(ScreenInstruction::SetInvisibleBorders(pane_id, value)) - } - pub fn screen_close_pane(pane_id: PaneId) -> Self { - Self::ToScreen(ScreenInstruction::ClosePane(pane_id)) - } - pub fn apply_layout(layout: PathBuf, pids: Vec<RawFd>) -> Self { - Self::ToScreen(ScreenInstruction::ApplyLayout(layout, pids)) - } - pub fn screen_new_tab(fd: RawFd) -> Self { - Self::ToScreen(ScreenInstruction::NewTab(fd)) - } - pub fn switch_tab_prev() -> Self { - Self::ToScreen(ScreenInstruction::SwitchTabPrev) - } - pub fn switch_tab_next() -> Self { - Self::ToScreen(ScreenInstruction::SwitchTabPrev) - } - pub fn screen_close_tab() -> Self { - Self::ToScreen(ScreenInstruction::CloseTab) - } - pub fn go_to_tab(tab_id: u32) -> Self { - Self::ToScreen(ScreenInstruction::GoToTab(tab_id)) - } - pub fn update_tab_name(tab_ids: Vec<u8>) -> Self { - Self::ToScreen(ScreenInstruction::UpdateTabName(tab_ids)) - } - pub fn change_mode(mode_info: ModeInfo) -> Self { - Self::ToScreen(ScreenInstruction::ChangeMode(mode_info)) - } - pub fn pty(fd: RawFd, bytes: VteBytes) -> Self { - Self::ToScreen(ScreenInstruction::PtyBytes(fd, bytes)) - } - pub fn terminal_resize(new_size: PositionAndSize) -> Self { - Self::ToScreen(ScreenInstruction::TerminalResize(new_size)) - } -} struct SessionMetaData { pub send_pty_instructions: SenderWithContext<PtyInstruction>, @@ -244,22 +118,13 @@ pub fn start_server(mut os_input: Box<dyn ServerOsApi>, opts: CliArgs) -> thread .send(ScreenInstruction::FocusNextPane) .unwrap(); } - ServerInstruction::ToScreen(instruction) => { - rlocked_sessions[rlocked_session] - .send_screen_instructions - .send(instruction) - .unwrap(); - } - ServerInstruction::ToPty(instruction) => { - rlocked_sessions[rlocked_session] - .send_pty_instructions - .send(instruction) - .unwrap(); + ServerInstruction::Action(action) => { + route_action(action, &rlocked_sessions[rlocked_session]); } - ServerInstruction::PluginUpdate(pid, event) => { + ServerInstruction::TerminalResize(new_size) => { rlocked_sessions[rlocked_session] - .send_plugin_instructions - .send(PluginInstruction::Update(pid, event)) + .send_screen_instructions + .send(ScreenInstruction::TerminalResize(new_size)) .unwrap(); } _ => { @@ -305,9 +170,6 @@ pub fn start_server(mut os_input: Box<dyn ServerOsApi>, opts: CliArgs) -> thread ServerInstruction::DoneUpdatingTabs => { os_input.send_to_client(ClientInstruction::DoneUpdatingTabs); } - ServerInstruction::ClientShouldExit => { - os_input.send_to_client(ClientInstruction::Exit); - } ServerInstruction::ClientExit => { drop( sessions @@ -316,9 +178,9 @@ pub fn start_server(mut os_input: Box<dyn ServerOsApi>, opts: CliArgs) -> thread .remove(&*session.read().unwrap()) .unwrap(), ); + os_input.send_to_client(ClientInstruction::Exit); os_input.server_exit(); let _ = router_thread.join(); - let _ = os_input.send_to_client(ClientInstruction::Exit); break; } ServerInstruction::Render(output) => { @@ -761,3 +623,144 @@ fn init_session( wasm_thread: Some(wasm_thread), } } + +fn route_action(action: Action, session: &SessionMetaData) { + match action { + Action::Write(val) => { + session + .send_screen_instructions + .send(ScreenInstruction::ClearScroll) + .unwrap(); + session + .send_screen_instructions + .send(ScreenInstruction::WriteCharacter(val)) + .unwrap(); + } + Action::SwitchToMode(mode) => { + session + .send_plugin_instructions + .send(PluginInstruction::Update( + None, + Event::ModeUpdate(get_mode_info(mode)), + )) + .unwrap(); + session + .send_screen_instructions + .send(ScreenInstruction::ChangeMode(get_mode_info(mode))) + .unwrap(); + session + .send_screen_instructions + .send(ScreenInstruction::Render) + .unwrap(); + } + Action::Resize(direction) => { + let screen_instr = match direction { + Direction::Left => ScreenInstruction::ResizeLeft, + Direction::Right => ScreenInstruction::ResizeRight, + Direction::Up => ScreenInstruction::ResizeUp, + Direction::Down => ScreenInstruction::ResizeDown, + }; + session.send_screen_instructions.send(screen_instr).unwrap(); + } + Action::SwitchFocus => { + session + .send_screen_instructions + .send(ScreenInstruction::SwitchFocus) + .unwrap(); + } + Action::FocusNextPane => { + session + .send_screen_instructions + .send(ScreenInstruction::FocusNextPane) + .unwrap(); + } + Action::FocusPreviousPane => { + session + .send_screen_instructions + .send(ScreenInstruction::FocusPreviousPane) + .unwrap(); + } + Action::MoveFocus(direction) => { + let screen_instr = match direction { + Direction::Left => ScreenInstruction::MoveFocusLeft, + Direction::Right => ScreenInstruction::MoveFocusRight, + Direction::Up => ScreenInstruction::MoveFocusUp, + Direction::Down => ScreenInstruction::MoveFocusDown, + }; + session.send_screen_instructions.send(screen_instr).unwrap(); + } + Action::ScrollUp => { + session + .send_screen_instructions + .send(ScreenInstruction::ScrollUp) + .unwrap(); + } + Action::ScrollDown => { + session + .send_screen_instructions + .send(ScreenInstruction::ScrollDown) + .unwrap(); + } + Action::ToggleFocusFullscreen => { + session + .send_screen_instructions + .send(ScreenInstruction::ToggleActiveTerminalFullscreen) + .unwrap(); + } + Action::NewPane(direction) => { + let pty_instr = match direction { + Some(Direction::Left) => PtyInstruction::SpawnTerminalVertically(None), + Some(Direction::Right) => PtyInstruction::SpawnTerminalVertically(None), + Some(Direction::Up) => PtyInstruction::SpawnTerminalHorizontally(None), + Some(Direction::Down) => PtyInstruction::SpawnTerminalHorizontally(None), + // No direction specified - try to put it in the biggest available spot + None => PtyInstruction::SpawnTerminal(None), + }; + session.send_pty_instructions.send(pty_instr).unwrap(); + } + Action::CloseFocus => { + session + .send_screen_instructions + .send(ScreenInstruction::CloseFocusedPane) + .unwrap(); + } + Action::NewTab => { + session + .send_pty_instructions + .send(PtyInstruction::NewTab) + .unwrap(); + } + Action::GoToNextTab => { + session + .send_screen_instructions + .send(ScreenInstruction::SwitchTabNext) + .unwrap(); + } + Action::GoToPreviousTab => { + session + .send_screen_instructions + .send(ScreenInstruction::SwitchTabPrev) + .unwrap(); + } + Action::Clo |