From b30ed86e2d2277c94a6655e9ebdeb8253805899d Mon Sep 17 00:00:00 2001 From: Sean Whitton Date: Fri, 16 Dec 2022 11:28:20 -0700 Subject: [PATCH] vc-git-checkin: Offer to unstage conflicting changes * lisp/vc/vc-git.el (vc-git-checkin): When committing a patch, if conflicting changes are already staged, offer to clear them, instead of just immediately failing with "Index not empty". --- lisp/vc/vc-git.el | 34 ++++++++++++++++++++++------------ 1 file changed, 22 insertions(+), 12 deletions(-) diff --git a/lisp/vc/vc-git.el b/lisp/vc/vc-git.el index 2876a983fb0..dcb51bb933f 100644 --- a/lisp/vc/vc-git.el +++ b/lisp/vc/vc-git.el @@ -1030,23 +1030,33 @@ vc-git-checkin (with-temp-buffer (vc-git-command (current-buffer) t nil "diff" "--cached") (goto-char (point-min)) - (let ((pos (point)) file-diff file-beg) + (let ((pos (point)) file-name file-diff file-beg) (while (not (eobp)) + (when (looking-at "^diff --git a/.+ b/\\(.+\\)") + (setq file-name (match-string 1))) (forward-line 1) ; skip current "diff --git" line (search-forward "diff --git" nil 'move) (move-beginning-of-line 1) (setq file-diff (buffer-substring pos (point))) - (if (and (setq file-beg (string-search - file-diff vc-git-patch-string)) - ;; Check that file diff ends with an empty string - ;; or the beginning of the next file diff. - (string-match-p "\\`\\'\\|\\`diff --git" - (substring - vc-git-patch-string - (+ file-beg (length file-diff))))) - (setq vc-git-patch-string - (string-replace file-diff "" vc-git-patch-string)) - (user-error "Index not empty")) + (cond ((and (setq file-beg (string-search + file-diff vc-git-patch-string)) + ;; Check that file diff ends with an empty string + ;; or the beginning of the next file diff. + (string-match-p "\\`\\'\\|\\`diff --git" + (substring + vc-git-patch-string + (+ file-beg (length file-diff))))) + (setq vc-git-patch-string + (string-replace file-diff "" vc-git-patch-string))) + ((and file-name + ;; Check the regexp extracted an actual file + ;; from the 'diff --git' line. + (file-exists-p (expand-file-name file-name root)) + (yes-or-no-p + (format "Unstage already-staged changes to %s?" + file-name))) + (vc-git-command nil 0 file-name "reset" "-q" "--")) + (t (user-error "Index not empty"))) (setq pos (point)))))) (let ((patch-file (make-nearby-temp-file "git-patch"))) (with-temp-file patch-file -- 2.30.2