diff --git a/crates/language/src/buffer.rs b/crates/language/src/buffer.rs index e6b0d48820b0db06de9cf96c4c887dbaff561607..353f3182c0b591cd9abea960ab4c534a05056dfc 100644 --- a/crates/language/src/buffer.rs +++ b/crates/language/src/buffer.rs @@ -1006,7 +1006,7 @@ impl Buffer { let old_text = old_text.to_string(); let line_ending = LineEnding::detect(&new_text); LineEnding::normalize(&mut new_text); - let changes = TextDiff::from_lines(old_text.as_str(), new_text.as_str()) + let changes = TextDiff::from_chars(old_text.as_str(), new_text.as_str()) .iter_all_changes() .map(|c| (c.tag(), c.value().len())) .collect::>(); diff --git a/crates/language/src/tests.rs b/crates/language/src/tests.rs index 937ff069305cabe280d4d5de5949ea5423181054..572f2b0ba88d31a62b26ab6660a4d6e203e94089 100644 --- a/crates/language/src/tests.rs +++ b/crates/language/src/tests.rs @@ -183,20 +183,23 @@ fn test_edit_events(cx: &mut gpui::MutableAppContext) { async fn test_apply_diff(cx: &mut gpui::TestAppContext) { let text = "a\nbb\nccc\ndddd\neeeee\nffffff\n"; let buffer = cx.add_model(|cx| Buffer::new(0, text, cx)); + let anchor = buffer.read_with(cx, |buffer, _| buffer.anchor_before(Point::new(3, 3))); let text = "a\nccc\ndddd\nffffff\n"; let diff = buffer.read_with(cx, |b, cx| b.diff(text.into(), cx)).await; buffer.update(cx, |buffer, cx| { buffer.apply_diff(diff, cx).unwrap(); + assert_eq!(buffer.text(), text); + assert_eq!(anchor.to_point(&buffer), Point::new(2, 3)); }); - cx.read(|cx| assert_eq!(buffer.read(cx).text(), text)); let text = "a\n1\n\nccc\ndd2dd\nffffff\n"; let diff = buffer.read_with(cx, |b, cx| b.diff(text.into(), cx)).await; buffer.update(cx, |buffer, cx| { buffer.apply_diff(diff, cx).unwrap(); + assert_eq!(buffer.text(), text); + assert_eq!(anchor.to_point(&buffer), Point::new(4, 4)); }); - cx.read(|cx| assert_eq!(buffer.read(cx).text(), text)); } #[gpui::test] diff --git a/crates/project/src/project_tests.rs b/crates/project/src/project_tests.rs index 4c5e9ef8e1b95994dbe9550b745ef6fb091d79b4..3dc4e9359f7dbb87ae5455a1a4ae5f6911ddcefd 100644 --- a/crates/project/src/project_tests.rs +++ b/crates/project/src/project_tests.rs @@ -2498,7 +2498,7 @@ async fn test_buffer_file_changes_on_disk(cx: &mut gpui::TestAppContext) { .collect::>(); assert_eq!( anchor_positions, - [Point::new(1, 1), Point::new(3, 1), Point::new(4, 0)] + [Point::new(1, 1), Point::new(3, 1), Point::new(3, 5)] ); }); diff --git a/crates/terminal/src/terminal.rs b/crates/terminal/src/terminal.rs index 2e06f8644170061be10ac0a3c3368b8b3134b176..45e46ce37885a958e0bb8241cea9d3c47459f2dc 100644 --- a/crates/terminal/src/terminal.rs +++ b/crates/terminal/src/terminal.rs @@ -4,11 +4,6 @@ pub mod mappings; pub mod modal; pub mod terminal_view; -#[cfg(test)] -use alacritty_terminal::term::cell::Cell; -#[cfg(test)] -use alacritty_terminal::Grid; - use alacritty_terminal::{ ansi::{ClearMode, Handler}, config::{Config, Program, PtyConfig, Scrolling}, @@ -629,11 +624,6 @@ impl Terminal { side, )))); } - - #[cfg(test)] - fn grid(&self) -> Grid { - self.term.lock().grid().clone() - } } impl Drop for Terminal { @@ -649,20 +639,6 @@ impl Entity for Terminal { #[cfg(test)] mod tests { pub mod terminal_test_context; - - use gpui::TestAppContext; - - use crate::tests::terminal_test_context::TerminalTestContext; - - ///Basic integration test, can we get the terminal to show up, execute a command, - //and produce noticable output? - #[gpui::test(retries = 5)] - async fn test_terminal(cx: &mut TestAppContext) { - let mut cx = TerminalTestContext::new(cx, true); - - cx.execute_and_wait("expr 3 + 4", |content, _cx| content.contains("7")) - .await; - } } //TODO Move this around and clean up the code @@ -742,28 +718,4 @@ mod alacritty_unix { pub fn default_shell(pw: &Passwd<'_>) -> Program { Program::Just(env::var("SHELL").unwrap_or_else(|_| pw.shell.to_owned())) } - - //Active entry with a work tree, worktree is a file, integration test with the strategy interface - #[gpui::test] - async fn active_entry_worktree_is_file_int(cx: &mut TestAppContext) { - //Setup variables - let mut cx = TerminalTestContext::new(cx, true); - let (project, workspace) = cx.blank_workspace().await; - let (_wt, _entry) = cx.create_folder_wt(project.clone(), "/root1/").await; - let (wt2, entry2) = cx.create_file_wt(project.clone(), "/root2.txt").await; - cx.insert_active_entry_for(wt2, entry2, project.clone()); - - //Test - cx.cx.update(|cx| { - let workspace = workspace.read(cx); - let active_entry = project.read(cx).active_entry(); - - assert!(active_entry.is_some()); - - let res = - get_working_directory(workspace, cx, WorkingDirectory::CurrentProjectDirectory); - let first = first_project_directory(workspace, cx); - assert_eq!(res, first); - }); - } } diff --git a/crates/terminal/src/terminal_view.rs b/crates/terminal/src/terminal_view.rs index 1d2043b2eea65a0282a4888fb877253b64d6041b..8acf1c233acf822931ce7864eef731d1c1446b1a 100644 --- a/crates/terminal/src/terminal_view.rs +++ b/crates/terminal/src/terminal_view.rs @@ -60,7 +60,14 @@ impl Entity for ErrorView { impl TerminalView { ///Create a new Terminal in the current working directory or the user's home directory pub fn deploy(workspace: &mut Workspace, _: &Deploy, cx: &mut ViewContext) { - let working_directory = get_working_directory(workspace, cx); + let strategy = cx + .global::() + .terminal_overrides + .working_directory + .clone() + .unwrap_or(WorkingDirectory::CurrentProjectDirectory); + + let working_directory = get_working_directory(workspace, cx, strategy); let view = cx.add_view(|cx| TerminalView::new(working_directory, false, cx)); workspace.add_item(Box::new(view), cx); } @@ -306,15 +313,14 @@ impl Item for TerminalView { } ///Get's the working directory for the given workspace, respecting the user's settings. -pub fn get_working_directory(workspace: &Workspace, cx: &AppContext) -> Option { - let wd_setting = cx - .global::() - .terminal_overrides - .working_directory - .clone() - .unwrap_or(WorkingDirectory::CurrentProjectDirectory); - let res = match wd_setting { - WorkingDirectory::CurrentProjectDirectory => current_project_directory(workspace, cx), +pub fn get_working_directory( + workspace: &Workspace, + cx: &AppContext, + strategy: WorkingDirectory, +) -> Option { + let res = match strategy { + WorkingDirectory::CurrentProjectDirectory => current_project_directory(workspace, cx) + .or_else(|| first_project_directory(workspace, cx)), WorkingDirectory::FirstProjectDirectory => first_project_directory(workspace, cx), WorkingDirectory::AlwaysHome => None, WorkingDirectory::Always { directory } => { @@ -374,7 +380,7 @@ mod tests { #[gpui::test] async fn no_worktree(cx: &mut TestAppContext) { //Setup variables - let mut cx = TerminalTestContext::new(cx, true); + let mut cx = TerminalTestContext::new(cx); let (project, workspace) = cx.blank_workspace().await; //Test cx.cx.read(|cx| { @@ -397,7 +403,7 @@ mod tests { async fn no_active_entry_worktree_is_file(cx: &mut TestAppContext) { //Setup variables - let mut cx = TerminalTestContext::new(cx, true); + let mut cx = TerminalTestContext::new(cx); let (project, workspace) = cx.blank_workspace().await; cx.create_file_wt(project.clone(), "/root.txt").await; @@ -420,7 +426,7 @@ mod tests { #[gpui::test] async fn no_active_entry_worktree_is_dir(cx: &mut TestAppContext) { //Setup variables - let mut cx = TerminalTestContext::new(cx, true); + let mut cx = TerminalTestContext::new(cx); let (project, workspace) = cx.blank_workspace().await; let (_wt, _entry) = cx.create_folder_wt(project.clone(), "/root/").await; @@ -443,7 +449,7 @@ mod tests { #[gpui::test] async fn active_entry_worktree_is_file(cx: &mut TestAppContext) { //Setup variables - let mut cx = TerminalTestContext::new(cx, true); + let mut cx = TerminalTestContext::new(cx); let (project, workspace) = cx.blank_workspace().await; let (_wt, _entry) = cx.create_folder_wt(project.clone(), "/root1/").await; let (wt2, entry2) = cx.create_file_wt(project.clone(), "/root2.txt").await; @@ -467,7 +473,7 @@ mod tests { #[gpui::test] async fn active_entry_worktree_is_dir(cx: &mut TestAppContext) { //Setup variables - let mut cx = TerminalTestContext::new(cx, true); + let mut cx = TerminalTestContext::new(cx); let (project, workspace) = cx.blank_workspace().await; let (_wt, _entry) = cx.create_folder_wt(project.clone(), "/root1/").await; let (wt2, entry2) = cx.create_folder_wt(project.clone(), "/root2/").await; diff --git a/crates/terminal/src/tests/terminal_test_context.rs b/crates/terminal/src/tests/terminal_test_context.rs index 70ebce2cbecb87fabccd5f8097edc51cfb03f7da..bee78e3ce0b3feeef432215ee6e02d5213668223 100644 --- a/crates/terminal/src/tests/terminal_test_context.rs +++ b/crates/terminal/src/tests/terminal_test_context.rs @@ -1,64 +1,19 @@ use std::{path::Path, time::Duration}; -use gpui::{AppContext, ModelHandle, ReadModelWith, TestAppContext, ViewHandle}; +use gpui::{ModelHandle, TestAppContext, ViewHandle}; -use itertools::Itertools; use project::{Entry, Project, ProjectPath, Worktree}; use workspace::{AppState, Workspace}; -use crate::{Terminal, TerminalBuilder, TerminalSize}; - pub struct TerminalTestContext<'a> { pub cx: &'a mut TestAppContext, - pub connection: Option>, } impl<'a> TerminalTestContext<'a> { - pub fn new(cx: &'a mut TestAppContext, term: bool) -> Self { + pub fn new(cx: &'a mut TestAppContext) -> Self { cx.set_condition_duration(Some(Duration::from_secs(5))); - let size_info = TerminalSize::default(); - - let connection = term.then(|| { - cx.add_model(|cx| { - TerminalBuilder::new(None, None, None, size_info) - .unwrap() - .subscribe(cx) - }) - }); - - TerminalTestContext { cx, connection } - } - - pub async fn execute_and_wait(&mut self, command: &str, f: F) -> String - where - F: Fn(String, &AppContext) -> bool, - { - let connection = self.connection.take().unwrap(); - - let command = command.to_string(); - connection.update(self.cx, |connection, _| { - connection.write_to_pty(command); - connection.write_to_pty("\r".to_string()); - }); - - connection - .condition(self.cx, |term, cx| { - let content = Self::grid_as_str(term); - - f(content, cx) - }) - .await; - - let res = self - .cx - .read_model_with(&connection, &mut |conn, _: &AppContext| { - Self::grid_as_str(conn) - }); - - self.connection = Some(connection); - - res + TerminalTestContext { cx } } ///Creates a worktree with 1 file: /root.txt @@ -131,17 +86,6 @@ impl<'a> TerminalTestContext<'a> { project.update(cx, |project, cx| project.set_active_path(Some(p), cx)); }); } - - fn grid_as_str(connection: &Terminal) -> String { - let content = connection.grid(); - - let lines = content.display_iter().group_by(|i| i.point.line.0); - lines - .into_iter() - .map(|(_, line)| line.map(|i| i.c).collect::()) - .collect::>() - .join("\n") - } } impl<'a> Drop for TerminalTestContext<'a> {