From 2c78cf349b94d69a4b027400d9d388992a4e4517 Mon Sep 17 00:00:00 2001 From: Thorsten Ball Date: Wed, 17 Apr 2024 11:25:53 +0200 Subject: [PATCH] Regenerate git blame info when buffer's dirty bit changed (#10670) This fixes the https://github.com/zed-industries/zed/issues/10583 by regenerating the blame information after the buffer is edited. It uses a debounce of 2seconds. Meaning that undone deletions show up again after 2secs. Release Notes: - Fixed `git blame` data not handling the undoing of deletions correctly. ([#10583](https://github.com/zed-industries/zed/issues/10583)). --- crates/editor/src/git/blame.rs | 36 ++++++++++++++++++++++++++++++---- 1 file changed, 32 insertions(+), 4 deletions(-) diff --git a/crates/editor/src/git/blame.rs b/crates/editor/src/git/blame.rs index ddfa14a7c46248d68cd1d3c7db376487a908290a..3bf56b3fc996dc39c557f2a7543f69b02beaf780 100644 --- a/crates/editor/src/git/blame.rs +++ b/crates/editor/src/git/blame.rs @@ -1,4 +1,4 @@ -use std::sync::Arc; +use std::{sync::Arc, time::Duration}; use anyhow::Result; use collections::HashMap; @@ -63,7 +63,8 @@ pub struct GitBlame { task: Task>, generated: bool, user_triggered: bool, - _refresh_subscription: Subscription, + regenerate_on_edit_task: Task>, + _regenerate_subscriptions: Vec, } impl GitBlame { @@ -81,7 +82,19 @@ impl GitBlame { &(), ); - let refresh_subscription = cx.subscribe(&project, { + let buffer_subscriptions = cx.subscribe(&buffer, |this, buffer, event, cx| match event { + language::Event::DirtyChanged => { + if !buffer.read(cx).is_dirty() { + this.generate(cx); + } + } + language::Event::Edited => { + this.regenerate_on_edit(cx); + } + _ => {} + }); + + let project_subscription = cx.subscribe(&project, { let buffer = buffer.clone(); move |this, _, event, cx| match event { @@ -116,7 +129,8 @@ impl GitBlame { commit_details: HashMap::default(), task: Task::ready(Ok(())), generated: false, - _refresh_subscription: refresh_subscription, + regenerate_on_edit_task: Task::ready(Ok(())), + _regenerate_subscriptions: vec![buffer_subscriptions, project_subscription], }; this.generate(cx); this @@ -310,8 +324,22 @@ impl GitBlame { }) }); } + + fn regenerate_on_edit(&mut self, cx: &mut ModelContext) { + self.regenerate_on_edit_task = cx.spawn(|this, mut cx| async move { + cx.background_executor() + .timer(REGENERATE_ON_EDIT_DEBOUNCE_INTERVAL) + .await; + + this.update(&mut cx, |this, cx| { + this.generate(cx); + }) + }); + } } +const REGENERATE_ON_EDIT_DEBOUNCE_INTERVAL: Duration = Duration::from_secs(2); + fn build_blame_entry_sum_tree(entries: Vec, max_row: u32) -> SumTree { let mut current_row = 0; let mut entries = SumTree::from_iter(