From 67a5266da3c52647471dbe23930adec5818491c7 Mon Sep 17 00:00:00 2001 From: mattwparas Date: Wed, 23 Aug 2023 18:58:33 -0700 Subject: [PATCH] engine shouldn't panic when helix.scm file fails to load --- helix-term/src/commands/engine.rs | 168 ++++++++++++++---------------- 1 file changed, 81 insertions(+), 87 deletions(-) diff --git a/helix-term/src/commands/engine.rs b/helix-term/src/commands/engine.rs index 0adfbebde..fecd9679e 100644 --- a/helix-term/src/commands/engine.rs +++ b/helix-term/src/commands/engine.rs @@ -16,6 +16,7 @@ use once_cell::sync::Lazy; use serde_json::Value; use steel::{ gc::unsafe_erased_pointers::CustomReference, + rerrs::ErrorKind, rvals::{ as_underlying_type, AsRefMutSteelValFromRef, AsRefSteelVal, FromSteelVal, IntoSteelVal, }, @@ -572,29 +573,94 @@ pub fn is_keymap(keymap: SteelVal) -> bool { fn run_initialization_script(cx: &mut Context) { log::info!("Loading init.scm..."); - let helix_module_path = helix_loader::steel_init_file(); + let helix_module_path = helix_loader::helix_module_file(); + + // TODO: Report the error from requiring the file! + ENGINE.with(|engine| { + let res = engine.borrow_mut().run(&format!( + r#"(require "{}")"#, + helix_module_path.to_str().unwrap() + )); + + // Present the error in the helix.scm loading + if let Err(e) = res { + present_error(cx, e); + return; + } + + let helix_path = + "__module-mangler".to_string() + helix_module_path.as_os_str().to_str().unwrap(); + + if let Ok(module) = engine.borrow_mut().extract_value(&helix_path) { + if let steel::rvals::SteelVal::HashMapV(m) = module { + let exported = m + .iter() + .filter(|(_, v)| v.is_function()) + .map(|(k, _)| { + if let steel::rvals::SteelVal::SymbolV(s) = k { + s.to_string() + } else { + panic!("Found a non symbol!") + } + }) + .collect::>(); + + let docs = exported + .iter() + .filter_map(|x| { + if let Ok(value) = engine.borrow_mut().run(&format!( + "(#%function-ptr-table-get #%function-ptr-table {})", + x + )) { + if let Some(SteelVal::StringV(doc)) = value.first() { + Some((x.to_string(), doc.to_string())) + } else { + None + } + } else { + None + } + }) + .collect::>(); + + *EXPORTED_IDENTIFIERS.identifiers.write().unwrap() = exported; + *EXPORTED_IDENTIFIERS.docs.write().unwrap() = docs; + } else { + present_error( + cx, + SteelErr::new( + ErrorKind::Generic, + "Unable to parse exported identifiers from helix module!".to_string(), + ), + ); - // These contents need to be registered with the path? - if let Ok(contents) = std::fs::read_to_string(&helix_module_path) { - let res = ENGINE.with(|x| { - x.borrow_mut() + return; + } + } + + let helix_module_path = helix_loader::steel_init_file(); + + // These contents need to be registered with the path? + if let Ok(contents) = std::fs::read_to_string(&helix_module_path) { + let res = engine + .borrow_mut() .run_with_reference_from_path::( cx, "*helix.cx*", &contents, helix_module_path, - ) - }); + ); - match res { - Ok(_) => {} - Err(e) => present_error(cx, e), - } + match res { + Ok(_) => {} + Err(e) => present_error(cx, e), + } - log::info!("Finished loading init.scm!") - } else { - log::info!("No init.scm found, skipping loading.") - } + log::info!("Finished loading init.scm!") + } else { + log::info!("No init.scm found, skipping loading.") + } + }); } pub static KEYBINDING_QUEUE: Lazy = @@ -1240,78 +1306,6 @@ fn configure_engine() -> std::rc::Rc>(); - - let docs = exported - .iter() - .filter_map(|x| { - if let Ok(value) = engine.run(&format!( - "(#%function-ptr-table-get #%function-ptr-table {})", - x - )) { - if let Some(SteelVal::StringV(doc)) = value.first() { - Some((x.to_string(), doc.to_string())) - } else { - None - } - } else { - None - } - - // if let Ok(steel::rvals::SteelVal::StringV(d)) = - // engine.extract_value(&(module_prefix.to_string() + x.as_str() + "__doc__")) - // { - // Some((x.to_string(), d.to_string())) - // } else { - // None - // } - }) - .collect::>(); - - *EXPORTED_IDENTIFIERS.identifiers.write().unwrap() = exported; - *EXPORTED_IDENTIFIERS.docs.write().unwrap() = docs; - } else { - panic!("Unable to parse exported identifiers from helix module!") - } - std::rc::Rc::new(std::cell::RefCell::new(engine)) }