From 51c15da3c32b2f0bf3da6db9bca9496d333ec15a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Bla=C5=BE=20Hrastnik?= <blaz@mxxn.io>
Date: Tue, 16 Mar 2021 23:14:51 +0900
Subject: [PATCH] Hold a reference to executor on the Editor type.

---
 helix-term/src/application.rs |  4 ++--
 helix-term/src/commands.rs    | 16 ++++++----------
 helix-term/src/ui/editor.rs   |  1 -
 helix-term/src/ui/mod.rs      |  4 ++--
 helix-view/src/editor.rs      | 13 ++++++++-----
 5 files changed, 18 insertions(+), 20 deletions(-)

diff --git a/helix-term/src/application.rs b/helix-term/src/application.rs
index f239a2f0..ef33db16 100644
--- a/helix-term/src/application.rs
+++ b/helix-term/src/application.rs
@@ -36,11 +36,11 @@ impl Application {
     pub fn new(mut args: Args, executor: &'static smol::Executor<'static>) -> Result<Self, Error> {
         let mut compositor = Compositor::new()?;
         let size = compositor.size();
-        let mut editor = Editor::new(size);
+        let mut editor = Editor::new(executor, size);
 
         let files = args.values_of_t::<PathBuf>("files").unwrap();
         for file in files {
-            editor.open(file, executor)?;
+            editor.open(file)?;
         }
 
         compositor.push(Box::new(ui::EditorView::new()));
diff --git a/helix-term/src/commands.rs b/helix-term/src/commands.rs
index 3e90fb63..34e4a813 100644
--- a/helix-term/src/commands.rs
+++ b/helix-term/src/commands.rs
@@ -28,7 +28,6 @@ use helix_lsp::lsp;
 pub struct Context<'a> {
     pub count: usize,
     pub editor: &'a mut Editor,
-    pub executor: &'static smol::Executor<'static>,
 
     pub callback: Option<crate::compositor::Callback>,
     pub on_next_key_callback: Option<Box<dyn FnOnce(&mut Context, KeyEvent)>>,
@@ -658,7 +657,6 @@ const COMMAND_LIST: &[&str] = &["write", "open", "quit"];
 
 // TODO: I, A, o and O can share a lot of the primitives.
 pub fn command_mode(cx: &mut Context) {
-    let executor = cx.executor;
     let prompt = Prompt::new(
         ":".to_owned(),
         |input: &str| {
@@ -695,11 +693,11 @@ pub fn command_mode(cx: &mut Context) {
 
             match *parts.as_slice() {
                 ["q"] | ["quit"] => {
-                    editor.close(editor.view().id, executor);
+                    editor.close(editor.view().id);
                     // editor.should_close = true,
                 }
                 ["o", path] | ["open", path] => {
-                    editor.open(path.into(), executor);
+                    editor.open(path.into());
                 }
                 ["w"] | ["write"] => {
                     // TODO: non-blocking via save() command
@@ -713,7 +711,7 @@ pub fn command_mode(cx: &mut Context) {
     cx.push_layer(Box::new(prompt));
 }
 pub fn file_picker(cx: &mut Context) {
-    let picker = ui::file_picker("./", cx.executor);
+    let picker = ui::file_picker("./");
     cx.push_layer(Box::new(picker));
 }
 
@@ -851,15 +849,13 @@ pub fn exit_select_mode(cx: &mut Context) {
 }
 
 fn goto(cx: &mut Context, locations: Vec<lsp::Location>) {
-    let executor = cx.executor;
     let doc = cx.doc();
 
     doc.mode = Mode::Normal;
 
     match locations.as_slice() {
         [location] => {
-            cx.editor
-                .open(PathBuf::from(location.uri.path()), cx.executor);
+            cx.editor.open(PathBuf::from(location.uri.path()));
             let doc = cx.doc();
             let definition_pos = location.range.start;
             let new_pos = helix_lsp::util::lsp_pos_to_pos(doc.text().slice(..), definition_pos);
@@ -875,7 +871,7 @@ fn goto(cx: &mut Context, locations: Vec<lsp::Location>) {
                     format!("{}:{}", file, line).into()
                 },
                 move |editor: &mut Editor, item| {
-                    editor.open(PathBuf::from(item.uri.path()), &executor);
+                    editor.open(PathBuf::from(item.uri.path()));
                     let mut doc = &mut editor.view_mut().doc;
                     let definition_pos = item.range.start;
                     let new_pos =
@@ -1274,7 +1270,7 @@ pub fn save(cx: &mut Context) {
     // Spawns an async task to actually do the saving. This way we prevent blocking.
 
     // TODO: handle save errors somehow?
-    cx.executor.spawn(cx.doc().save()).detach();
+    cx.editor.executor.spawn(cx.doc().save()).detach();
 }
 
 pub fn completion(cx: &mut Context) {
diff --git a/helix-term/src/ui/editor.rs b/helix-term/src/ui/editor.rs
index eb951a26..b79b05e3 100644
--- a/helix-term/src/ui/editor.rs
+++ b/helix-term/src/ui/editor.rs
@@ -436,7 +436,6 @@ impl Component for EditorView {
 
                 let mode = view.doc.mode();
                 let mut cxt = commands::Context {
-                    executor: cx.executor,
                     editor: &mut cx.editor,
                     count: 1,
                     callback: None,
diff --git a/helix-term/src/ui/mod.rs b/helix-term/src/ui/mod.rs
index b175c646..f2376504 100644
--- a/helix-term/src/ui/mod.rs
+++ b/helix-term/src/ui/mod.rs
@@ -73,7 +73,7 @@ pub fn regex_prompt(
 }
 
 use std::path::{Path, PathBuf};
-pub fn file_picker(root: &str, ex: &'static smol::Executor) -> Picker<PathBuf> {
+pub fn file_picker(root: &str) -> Picker<PathBuf> {
     use ignore::Walk;
     // TODO: determine root based on git root
     let files = Walk::new(root).filter_map(|entry| match entry {
@@ -98,7 +98,7 @@ pub fn file_picker(root: &str, ex: &'static smol::Executor) -> Picker<PathBuf> {
             path.strip_prefix("./").unwrap().to_str().unwrap().into()
         },
         move |editor: &mut Editor, path: &PathBuf| {
-            editor.open(path.into(), ex);
+            editor.open(path.into());
         },
     )
 }
diff --git a/helix-view/src/editor.rs b/helix-view/src/editor.rs
index 5c94df27..9b32b335 100644
--- a/helix-view/src/editor.rs
+++ b/helix-view/src/editor.rs
@@ -14,10 +14,11 @@ pub struct Editor {
     pub count: Option<usize>,
     pub theme: Theme,
     pub language_servers: helix_lsp::Registry,
+    pub executor: &'static smol::Executor<'static>,
 }
 
 impl Editor {
-    pub fn new(mut area: tui::layout::Rect) -> Self {
+    pub fn new(executor: &'static smol::Executor<'static>, mut area: tui::layout::Rect) -> Self {
         let theme = Theme::default();
         let language_servers = helix_lsp::Registry::new();
 
@@ -29,10 +30,11 @@ impl Editor {
             count: None,
             theme,
             language_servers,
+            executor,
         }
     }
 
-    pub fn open(&mut self, path: PathBuf, executor: &smol::Executor) -> Result<(), Error> {
+    pub fn open(&mut self, path: PathBuf) -> Result<(), Error> {
         let existing_view = self
             .tree
             .views()
@@ -49,7 +51,7 @@ impl Editor {
         let language_server = doc
             .language
             .as_ref()
-            .and_then(|language| self.language_servers.get(language, &executor));
+            .and_then(|language| self.language_servers.get(language, self.executor));
 
         if let Some(language_server) = language_server {
             doc.set_language_server(Some(language_server.clone()));
@@ -74,17 +76,18 @@ impl Editor {
         Ok(())
     }
 
-    pub fn close(&mut self, id: Key, executor: &smol::Executor) {
+    pub fn close(&mut self, id: Key) {
         let view = self.tree.get(self.tree.focus);
         // get around borrowck issues
         let language_servers = &mut self.language_servers;
+        let executor = self.executor;
 
         let doc = &view.doc;
 
         let language_server = doc
             .language
             .as_ref()
-            .and_then(|language| language_servers.get(language, &executor));
+            .and_then(|language| language_servers.get(language, executor));
 
         if let Some(language_server) = language_server {
             smol::block_on(language_server.text_document_did_close(doc.identifier())).unwrap();