Add `OpenTextEditor` event
Dependencies
- [2]
WFWTKCJNCreate initial Visual Studio Code extension - [3]
3YGYMEXVCreate `event_loop` module - [4]
NB2MF3MYAdd `OpenWorkspaceFolder` event - [5]
OUADGWKRCreate fully-initialized `SourceControl` object in `event_loop` - [6]
2ZAM5V35Move event handling into modules - [7]
TWEUQ64DMove threadsafe function builder logic into function-specific modules - [8]
QY4Z5ZXZRefactor `event_loop/threadsafe_function` file into `event_loop::js_function` module - [9]
IBVCQSSGUse `External` to wrap `initialize_source_control` arguments - [10]
IDY5SNLOUpdate source control resource states in event loop - [11]
3RNQI5RXRefactor `provide_file_decoration` to return a `Promise` resolved by `event_loop`
Change contents
- edit in editors/vscode/src/lib.rs at line 238
for text_editor in &visible_text_editors {let uri = UriAbsoluteString::try_from(text_editor.get_document()?.get_uri()?.to_string()?).map_err(|error| napi::Error::from_reason(format!("Failed to parse URI: {error}")))?;event_loop::send(Event::OpenTextEditor {uri,text_editor: text_editor.create_ref()?,});} - replacement in editors/vscode/src/event_loop/mod.rs at line 6
use iri_string::types::UriAbsoluteStr;use iri_string::types::{UriAbsoluteStr, UriAbsoluteString}; - replacement in editors/vscode/src/event_loop/mod.rs at line 24
open_editors: HashMap<Utf8PathBuf, vscode_sys::reference::TextEditorRef>,open_editors: HashMap<Utf8PathBuf, Rc<vscode_sys::reference::TextEditorRef>>, - replacement in editors/vscode/src/event_loop/mod.rs at line 35
fn find_repository<'uri>(&'uri self,fn find_repository_root<'uri>(&self, - replacement in editors/vscode/src/event_loop/mod.rs at line 38
) -> Option<(&'uri Utf8Path, &'uri Repository)> {) -> Option<(&'uri Utf8Path, &'uri Utf8Path)> { - replacement in editors/vscode/src/event_loop/mod.rs at line 43
for ancestor in Utf8Path::new(uri.path_str()).ancestors() {if let Some(repository) = self.repositories.get(ancestor) {return Some((ancestor, repository));let uri_path = Utf8Path::new(uri.path_str());for ancestor in uri_path.ancestors() {if self.repositories.contains_key(ancestor) {return Some((ancestor, uri_path.strip_prefix(ancestor).unwrap())); - edit in editors/vscode/src/event_loop/mod.rs at line 51
}#[tracing::instrument(skip(self))]fn get_repository<'uri>(&self,uri: &'uri UriAbsoluteStr,) -> Option<(&'uri Utf8Path, &'uri Utf8Path, &Repository)> {self.find_repository_root(uri).map(|(repository_path, relative_path)| {(repository_path,relative_path,self.repositories.get(repository_path).unwrap(),)})}#[tracing::instrument(skip(self))]fn get_repository_mut<'uri>(&mut self,uri: &'uri UriAbsoluteStr,) -> Option<(&'uri Utf8Path, &'uri Utf8Path, &mut Repository)> {self.find_repository_root(uri).map(|(repository_path, relative_path)| {(repository_path,relative_path,self.repositories.get_mut(repository_path).unwrap(),)}) - edit in editors/vscode/src/event_loop/mod.rs at line 115
).await}Event::OpenTextEditor { uri, text_editor } => {event::open_text_editor::handle(uri,text_editor,&mut extension_state,&js_functions, - edit in editors/vscode/src/event_loop/js_function/mod.rs at line 9
pub mod get_text_editor_contents; - edit in editors/vscode/src/event_loop/js_function/mod.rs at line 14
get_text_editor_contents: get_text_editor_contents::Prototype, - edit in editors/vscode/src/event_loop/js_function/mod.rs at line 23
get_text_editor_contents: get_text_editor_contents::build(env)?, - edit in editors/vscode/src/event_loop/js_function/mod.rs at line 28
}pub async fn get_text_editor_contents(&self,text_editor_reference: &Rc<vscode_sys::reference::TextEditorRef>,) -> Result<String, napi::Error> {let arguments = get_text_editor_contents::Arguments {text_editor_reference: Rc::clone(text_editor_reference),};self.get_text_editor_contents.call_async(External::new(arguments)).await - file addition: get_text_editor_contents.rs[8.435]
use std::rc::Rc;use napi::bindgen_prelude::{External, FunctionCallContext};use napi::threadsafe_function::ThreadsafeFunction;use crate::vscode_sys;pub struct Arguments {pub text_editor_reference: Rc<vscode_sys::reference::TextEditorRef>,}pub type Prototype = ThreadsafeFunction<External<Arguments>,String,External<Arguments>,napi::Status,false,false,0,>;pub fn build(env: &napi::Env) -> Result<Prototype, napi::Error> {env.create_function_from_closure("get_text_editor_contents", callback)?.build_threadsafe_function().build()}fn callback(function_call_context: FunctionCallContext) -> Result<String, napi::Error> {let (external,): (&External<Arguments>,) = function_call_context.args()?;let Arguments {text_editor_reference,} = &**external;let text_editor = text_editor_reference.get_inner(function_call_context.env)?;let document = text_editor.get_document()?;document.get_text(None)} - edit in editors/vscode/src/event_loop/event/request_file_decoration.rs at line 1
use camino::Utf8Path; - replacement in editors/vscode/src/event_loop/event/request_file_decoration.rs at line 58
let Some((repository_path, repository)) = extension_state.find_repository(uri) else {let Some((_repository_path, relative_path, repository)) = extension_state.get_repository(uri)else { - replacement in editors/vscode/src/event_loop/event/request_file_decoration.rs at line 64
let decoration_path = match Utf8Path::new(uri.path_str()).strip_prefix(repository_path) {Ok(decoration_path) => decoration_path,Err(error) => {tracing::error!(message = "Failed to strip repository prefix from path",?repository_path,?uri,?error);return None;}};repository.repository.get_path_state(decoration_path)repository.repository.get_path_state(relative_path) - file addition: open_text_editor.rs[6.332]
use std::rc::Rc;use iri_string::types::UriAbsoluteString;use crate::event_loop::ExtensionState;use crate::event_loop::js_function::Functions;use crate::vscode_sys;#[tracing::instrument(skip(text_editor_reference, extension_state, js_functions))]pub async fn handle(uri: UriAbsoluteString,text_editor_reference: vscode_sys::reference::TextEditorRef,extension_state: &mut ExtensionState,js_functions: &Functions,) {let Some((repository_path, relative_path, repository)) =extension_state.get_repository_mut(&uri)else {// TODO: keep track of unassigned text editors in case they later become part of a repositorytracing::info!(message = "Ignoring text editor");return;};if repository.open_editors.contains_key(relative_path) {tracing::debug!(message = "Ignoring existing text editor",?repository_path,?relative_path);} else {let text_editor = Rc::new(text_editor_reference);let editor_contents = match js_functions.get_text_editor_contents(&text_editor).await {Ok(contents) => contents,Err(error) => {tracing::error!(message = "Failed to get text editor contents", ?error);return;}};if let Err(error) = repository.repository.create_open_file(relative_path.to_path_buf(), editor_contents){tracing::error!(message = "Failed to create open file", ?error);};repository.open_editors.insert(relative_path.to_path_buf(), text_editor);tracing::info!(message = "Opened new text editor",?repository_path,?relative_path);}} - edit in editors/vscode/src/event_loop/event/mod.rs at line 3
use crate::vscode_sys; - edit in editors/vscode/src/event_loop/event/mod.rs at line 6
pub mod open_text_editor; - edit in editors/vscode/src/event_loop/event/mod.rs at line 15
OpenTextEditor {uri: UriAbsoluteString,text_editor: vscode_sys::reference::TextEditorRef,},