[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[elpa] externals/diff-hl 2c07ababaa: Allow updating indicators asynchron
|
From: |
ELPA Syncer |
|
Subject: |
[elpa] externals/diff-hl 2c07ababaa: Allow updating indicators asynchronously (without blocking Emacs) (#207) |
|
Date: |
Sun, 21 Jan 2024 18:57:51 -0500 (EST) |
branch: externals/diff-hl
commit 2c07ababaa621c593fbd2746551311e14ce5af55
Author: Wai Hon Law <whhone@gmail.com>
Commit: GitHub <noreply@github.com>
Allow updating indicators asynchronously (without blocking Emacs) (#207)
Problem: On a slow VC backend, `diff-hl-mode` freezes Emacs because
`(diff-hl-changes)` takes a long time.
Changes:
- Add a custom variable `diff-hl-update-async`.
- When it's non-nil, update inside a separate thread.
- Log a message if diff-hl--update throws an error.
- Add a TODO to debounce if a thread is already running.
---
diff-hl.el | 26 ++++++++++++++++++++++++++
test/diff-hl-test.el | 25 +++++++++++++++++++++++++
2 files changed, 51 insertions(+)
diff --git a/diff-hl.el b/diff-hl.el
index 2a8bce556b..c654e73e01 100644
--- a/diff-hl.el
+++ b/diff-hl.el
@@ -194,6 +194,14 @@ the NEW revision is not specified (meaning, the diff is
against
the current version of the file)."
:type 'boolean)
+(defcustom diff-hl-update-async nil
+ "When non-nil, `diff-hl-update' will run asynchronously.
+
+This can help prevent Emacs from freezing, especially by a slow version
+control (VC) backend. Remote files will not be affected since this feature
+does not work reliably with them."
+ :type 'boolean)
+
(defvar diff-hl-reference-revision nil
"Revision to diff against. nil means the most recent one.")
@@ -384,6 +392,24 @@ the current version of the file)."
(nreverse res))))
(defun diff-hl-update ()
+ "Updates the diff-hl overlay in a thread."
+ (if (and diff-hl-update-async
+ ;; Disable threading on the remote file as it is unreliable.
+ (not (file-remote-p default-directory)))
+ ;; TODO: debounce if a thread is already running.
+ (make-thread 'diff-hl--update-safe "diff-hl--update-safe")
+ (diff-hl--update)))
+
+(defun diff-hl--update-safe ()
+ "Updates the diff-hl overlay. It handles and logs when an error is signaled."
+ (condition-case err
+ (diff-hl--update)
+ (error
+ (message "An error occurred in diff-hl--update: %S" err)
+ nil)))
+
+(defun diff-hl--update ()
+ "Updates the diff-hl overlay."
(let ((changes (diff-hl-changes))
(current-line 1))
(diff-hl-remove-overlays)
diff --git a/test/diff-hl-test.el b/test/diff-hl-test.el
index d255f0a147..412532f01a 100644
--- a/test/diff-hl-test.el
+++ b/test/diff-hl-test.el
@@ -126,6 +126,31 @@
(should (looking-at "added"))
(should-error (diff-hl-next-hunk) :type 'user-error)))
+(diff-hl-deftest diff-hl-indirect-buffer-move-async ()
+ (diff-hl-test-in-source
+ (let ((diff-hl-update-async t))
+ (narrow-to-region (point-min) (point-max))
+ (goto-char (point-min))
+ (kill-whole-line 3)
+ (goto-char (point-max))
+ (insert "added\n")
+ (save-buffer)
+ (diff-hl-mode 1)
+
+ ;; wait for all thread to complete.
+ (dolist (thread (all-threads))
+ (unless (eq thread main-thread)
+ (thread-join thread)))
+
+ (diff-hl-previous-hunk)
+ (should (looking-at "added"))
+ (diff-hl-previous-hunk)
+ (should (looking-at "function2"))
+ (should-error (diff-hl-previous-hunk) :type 'user-error)
+ (diff-hl-next-hunk)
+ (should (looking-at "added"))
+ (should-error (diff-hl-next-hunk) :type 'user-error))))
+
(diff-hl-deftest diff-hl-can-ignore-staged-changes ()
(diff-hl-test-in-source
(goto-char (point-min))
| [Prev in Thread] |
Current Thread |
[Next in Thread] |
- [elpa] externals/diff-hl 2c07ababaa: Allow updating indicators asynchronously (without blocking Emacs) (#207),
ELPA Syncer <=