diff options
| author | Sean Whitton | 2025-07-06 13:43:24 +0100 |
|---|---|---|
| committer | Sean Whitton | 2025-07-06 14:03:31 +0100 |
| commit | 7a0bfa3ee7fa447a0fe994ac8f64bcb5752cacb2 (patch) | |
| tree | f93da5808cc0e874c543bd7cd352f6a5fbcd3d11 | |
| parent | 67ddf2157659e9cd6fb9b109049da66c7abe4ffb (diff) | |
| download | emacs-7a0bfa3ee7fa447a0fe994ac8f64bcb5752cacb2.tar.gz emacs-7a0bfa3ee7fa447a0fe994ac8f64bcb5752cacb2.zip | |
vc-checkin: Check whether the fileset or patches have changed
* lisp/vc/vc-dispatcher.el (vc-finish-logentry): Delay popping
to vc-parent-buffer until after calling the log operation.
That way if the log operation exits early, the current buffer
remains *vc-log*.
(vc-dir-marked-files, dired-get-marked-files): Declare.
(vc-dispatcher--explicit-marks-p): New function.
* lisp/vc/vc.el (vc-checkin): Check the user isn't likely to be
surprised by what is included in the checkin. Specifically,
check whether the fileset or patches implied by vc-parent-buffer
are unchanged.
* doc/emacs/maintaining.texi (VC With A Merging VCS): Explain
how the fileset or patch string is fixed once *vc-log* pops up.
| -rw-r--r-- | doc/emacs/maintaining.texi | 17 | ||||
| -rw-r--r-- | lisp/vc/vc-dispatcher.el | 21 | ||||
| -rw-r--r-- | lisp/vc/vc.el | 42 |
3 files changed, 72 insertions, 8 deletions
diff --git a/doc/emacs/maintaining.texi b/doc/emacs/maintaining.texi index 12770f218ca..ea7b8794bbc 100644 --- a/doc/emacs/maintaining.texi +++ b/doc/emacs/maintaining.texi | |||
| @@ -572,6 +572,23 @@ then applies the changes to the respective files and commits the changes | |||
| 572 | after popping up the @file{*vc-log*} buffer to allow you to type a | 572 | after popping up the @file{*vc-log*} buffer to allow you to type a |
| 573 | suitable commit log message. | 573 | suitable commit log message. |
| 574 | 574 | ||
| 575 | Once you type @kbd{C-x v v}, the fileset or patches cannot be changed | ||
| 576 | without first cancelling the commit by typing @kbd{C-c C-k} in the | ||
| 577 | @file{*vc-log*} buffer. For example, if you change which files are | ||
| 578 | marked in the @file{*vc-dir*} buffer after Emacs has already popped up | ||
| 579 | the @file{*vc-log*} buffer, the old fileset will remain in effect for | ||
| 580 | this commit. (This is in contrast to changes made to the | ||
| 581 | @emph{contents} of files in the fileset: all such changes will be | ||
| 582 | included in the commit even if they are made after Emacs has popped up | ||
| 583 | the @file{*vc-dir*} buffer.) | ||
| 584 | |||
| 585 | When you cancel a commit, Emacs saves your log message. This means that | ||
| 586 | if you need to adjust the fileset or patches, it is easy to restart the | ||
| 587 | commit operation again: type @w{@kbd{C-c C-k C-x v v M-p}}. Here | ||
| 588 | @kbd{C-c C-k} cancels the commit, @kbd{C-x v v} initiates another with | ||
| 589 | the new fileset or patches, and finally @kbd{M-p} recalls your previous | ||
| 590 | log message. | ||
| 591 | |||
| 575 | With modern decentralized version control systems (Git, Mercurial, | 592 | With modern decentralized version control systems (Git, Mercurial, |
| 576 | etc.), the changes are committed locally and not automatically | 593 | etc.), the changes are committed locally and not automatically |
| 577 | propagated to the upstream repository (which is usually on a remote | 594 | propagated to the upstream repository (which is usually on a remote |
diff --git a/lisp/vc/vc-dispatcher.el b/lisp/vc/vc-dispatcher.el index be50e51ed5f..97f1971dd1d 100644 --- a/lisp/vc/vc-dispatcher.el +++ b/lisp/vc/vc-dispatcher.el | |||
| @@ -864,18 +864,13 @@ the buffer contents as a comment." | |||
| 864 | ;; save the parameters held in buffer-local variables | 864 | ;; save the parameters held in buffer-local variables |
| 865 | (let ((logbuf (current-buffer)) | 865 | (let ((logbuf (current-buffer)) |
| 866 | (log-operation vc-log-operation) | 866 | (log-operation vc-log-operation) |
| 867 | ;; FIXME: When coming from VC-Dir, we should check that the | ||
| 868 | ;; set of selected files is still equal to vc-log-fileset, | ||
| 869 | ;; to avoid surprises. | ||
| 870 | (log-fileset vc-log-fileset) | 867 | (log-fileset vc-log-fileset) |
| 871 | (log-entry (buffer-string)) | 868 | (log-entry (buffer-string)) |
| 872 | (after-hook vc-log-after-operation-hook)) | 869 | (after-hook vc-log-after-operation-hook)) |
| 873 | (pop-to-buffer vc-parent-buffer) | ||
| 874 | ;; OK, do it to it | 870 | ;; OK, do it to it |
| 875 | (save-excursion | 871 | (with-current-buffer vc-parent-buffer |
| 876 | (funcall log-operation | 872 | (funcall log-operation log-fileset log-entry)) |
| 877 | log-fileset | 873 | (pop-to-buffer vc-parent-buffer) |
| 878 | log-entry)) | ||
| 879 | (setq vc-log-operation nil) | 874 | (setq vc-log-operation nil) |
| 880 | 875 | ||
| 881 | ;; Quit windows on logbuf. | 876 | ;; Quit windows on logbuf. |
| @@ -896,6 +891,16 @@ the buffer contents as a comment." | |||
| 896 | (derived-mode-p 'diff-mode) | 891 | (derived-mode-p 'diff-mode) |
| 897 | (derived-mode-p 'log-view-mode))) | 892 | (derived-mode-p 'log-view-mode))) |
| 898 | 893 | ||
| 894 | (declare-function vc-dir-marked-files "vc-dir") | ||
| 895 | (declare-function dired-get-marked-files "dired") | ||
| 896 | |||
| 897 | (defun vc-dispatcher--explicit-marks-p () | ||
| 898 | "Are any files in the directory browser explicitly marked?" | ||
| 899 | (or (and (derived-mode-p 'vc-dir-mode) | ||
| 900 | (vc-dir-marked-files)) | ||
| 901 | (and (derived-mode-p 'dired-mode) | ||
| 902 | (length> (dired-get-marked-files nil nil nil t) 1)))) | ||
| 903 | |||
| 899 | ;; These are unused. | 904 | ;; These are unused. |
| 900 | ;; (defun vc-dispatcher-in-fileset-p (fileset) | 905 | ;; (defun vc-dispatcher-in-fileset-p (fileset) |
| 901 | ;; (let ((member nil)) | 906 | ;; (let ((member nil)) |
diff --git a/lisp/vc/vc.el b/lisp/vc/vc.el index 824959fc231..a6a4aa50579 100644 --- a/lisp/vc/vc.el +++ b/lisp/vc/vc.el | |||
| @@ -1953,6 +1953,48 @@ Runs the normal hooks `vc-before-checkin-hook' and `vc-checkin-hook'." | |||
| 1953 | (lambda () | 1953 | (lambda () |
| 1954 | (vc-call-backend backend 'log-edit-mode)) | 1954 | (vc-call-backend backend 'log-edit-mode)) |
| 1955 | (lambda (files comment) | 1955 | (lambda (files comment) |
| 1956 | ;; Check the user isn't likely to be surprised by what is included | ||
| 1957 | ;; in the checkin. Once a log operation is started, the fileset | ||
| 1958 | ;; or patch string is locked in. In particular, it's probably too | ||
| 1959 | ;; late to offer to change it now -- checks in hooks and/or the | ||
| 1960 | ;; backend's Log Edit derived mode have all already okayed the | ||
| 1961 | ;; checkin. Restarting with the new fileset or patch is easy. | ||
| 1962 | (let* ((start-again | ||
| 1963 | (substitute-command-keys "\\[vc-next-action] to check in again")) | ||
| 1964 | (instructions | ||
| 1965 | (substitute-command-keys | ||
| 1966 | (string-join | ||
| 1967 | (list "type \\<log-edit-mode-map>\\[log-edit-kill-buffer] to cancel" | ||
| 1968 | start-again | ||
| 1969 | "\\[log-edit-previous-comment] to recall your message") | ||
| 1970 | ", ")))) | ||
| 1971 | (cond (patch-string | ||
| 1972 | (unless (or (not (derived-mode-p 'diff-mode)) | ||
| 1973 | (equal patch-string (buffer-string)) | ||
| 1974 | (yes-or-no-p | ||
| 1975 | (format-message "Patch in buffer \"%s\" \ | ||
| 1976 | has changed; continue with old patch?" (current-buffer)))) | ||
| 1977 | (user-error "%s %s" | ||
| 1978 | "To check in the new patch" instructions))) | ||
| 1979 | ((vc-dispatcher-browsing) | ||
| 1980 | (unless (or (and (length= files 1) | ||
| 1981 | ;; If no files in the dispatcher were | ||
| 1982 | ;; marked and it was just that point | ||
| 1983 | ;; moved to a different line, we don't | ||
| 1984 | ;; want to bother the user. This isn't | ||
| 1985 | ;; foolproof because we don't know | ||
| 1986 | ;; whether FILES was selected by means | ||
| 1987 | ;; of marking a single file or the | ||
| 1988 | ;; implicit selection of the file at | ||
| 1989 | ;; point in the absence of any marks. | ||
| 1990 | (not (vc-dispatcher--explicit-marks-p))) | ||
| 1991 | (equal files (cadr (vc-deduce-fileset))) | ||
| 1992 | (yes-or-no-p | ||
| 1993 | (format-message "Selected file(s) in buffer \"%s\" \ | ||
| 1994 | have changed; continue with old fileset?" (current-buffer)))) | ||
| 1995 | (user-error "%s %s" | ||
| 1996 | "To use the new fileset" instructions))))) | ||
| 1997 | |||
| 1956 | ;; "This log message intentionally left almost blank". | 1998 | ;; "This log message intentionally left almost blank". |
| 1957 | ;; RCS 5.7 gripes about whitespace-only comments too. | 1999 | ;; RCS 5.7 gripes about whitespace-only comments too. |
| 1958 | (unless (and comment (string-match "[^\t\n ]" comment)) | 2000 | (unless (and comment (string-match "[^\t\n ]" comment)) |