From 243b8aac69d271a1a742483bf93ff992748b131b Mon Sep 17 00:00:00 2001 From: Eshel Yaron Date: Tue, 24 Jun 2025 08:27:46 +0200 Subject: [PATCH] (refactor-apply-edits-dtrt): New function. --- lisp/emacs-lisp/scope.el | 8 +++----- lisp/progmodes/cc-langs.el | 2 -- lisp/progmodes/cc-mode.el | 4 ---- lisp/progmodes/refactor.el | 28 ++++++++++++++++++++++++++-- 4 files changed, 29 insertions(+), 13 deletions(-) diff --git a/lisp/emacs-lisp/scope.el b/lisp/emacs-lisp/scope.el index 504eddecc48..980b45d0b9f 100644 --- a/lisp/emacs-lisp/scope.el +++ b/lisp/emacs-lisp/scope.el @@ -696,9 +696,6 @@ Optional argument LOCAL is a local context to extend." (scope-1 local arg))))) ((consp arg) (scope-1 local arg)))) -(defun scope-declare-function (local fn _file arglist _fileonly) - (scope-defun local fn (when (listp arglist) arglist) nil)) - (defun scope-loop-for-and (local rest) (if (eq (scope-sym-bare (car rest)) 'and) (scope-loop-for local local (cadr rest) (cddr rest)) @@ -1924,8 +1921,9 @@ a (possibly empty) list of safe macros.") (scope-1 l expr) (scope-cl-lambda l args body)) -(scope-define-macro-analyzer declare-function (l fn file &optional arglist fileonly) - (scope-declare-function l fn file arglist fileonly)) +(scope-define-macro-analyzer declare-function (l &optional fn _file arglist _fileonly) + (scope-report-s fn 'function) + (scope-lambda l (and (listp arglist) arglist) nil)) (scope-define-macro-analyzer cl-block (l name &rest body) (scope-block l name body)) diff --git a/lisp/progmodes/cc-langs.el b/lisp/progmodes/cc-langs.el index dc9b8b7aed9..668891ab6fc 100644 --- a/lisp/progmodes/cc-langs.el +++ b/lisp/progmodes/cc-langs.el @@ -114,8 +114,6 @@ ;;; Code: ;; For Emacs < 22.2. -(eval-and-compile - (unless (fboundp 'declare-function) (defmacro declare-function (&rest _)))) (eval-when-compile (let ((load-path diff --git a/lisp/progmodes/cc-mode.el b/lisp/progmodes/cc-mode.el index 494a7506660..ef7e99a04cb 100644 --- a/lisp/progmodes/cc-mode.el +++ b/lisp/progmodes/cc-mode.el @@ -88,10 +88,6 @@ ;;; Code: -;; For Emacs < 22.2. -(eval-and-compile - (unless (fboundp 'declare-function) (defmacro declare-function (&rest _r)))) - (eval-when-compile (let ((load-path (if (and (boundp 'byte-compile-dest-file) diff --git a/lisp/progmodes/refactor.el b/lisp/progmodes/refactor.el index 6a0fe315851..93c0a1c9d98 100644 --- a/lisp/progmodes/refactor.el +++ b/lisp/progmodes/refactor.el @@ -32,7 +32,7 @@ "Refactor code." :group 'programming) -(defcustom refactor-apply-edits-function #'refactor-apply-edits-at-once +(defcustom refactor-apply-edits-function #'refactor-apply-edits-dtrt "Function to use for applying edits during refactoring. `refactor-apply-edits' calls this function with one argument, a list of @@ -44,6 +44,7 @@ at BEG afterwards. If this function applies a replacement, it should run hook `refactor-replacement-functions' with the corresponding TOKEN as an argument while BUFFER is current." :type '(choice (const :tag "Apply edits at once" refactor-apply-edits-at-once) + (const :tag "Do the right thing" refactor-apply-edits-dtrt) (const :tag "Query about each edit" refactor-query-apply-edits) (const :tag "Display edits as diff" refactor-display-edits-as-diff) (function :tag "Custom function"))) @@ -283,6 +284,23 @@ argument is the token corresponding to that text replacement.") (dolist (token tokens) (run-hook-with-args 'refactor-replacement-functions token))))) +(defun refactor-diff-buffer-file-name (buf) + (or (and (not (buffer-modified-p buf)) + (buffer-file-name buf)) + (with-current-buffer buf + (let ((tempfile (make-temp-file "buffer-content-"))) + (write-region nil nil tempfile nil 'nomessage) + tempfile)))) + +(defun refactor-diff (old old-label new new-label out) + "Insert diff betweeen OLD and NEW buffers into OUT buffer. + +OLD-LABEL and NEW-LABEL are the labels to use for OLD and NEW, +respectively." + (call-process + diff-command nil out nil "-U" "2" "--label" old-label "--label" new-label + (refactor-diff-buffer-file-name old) (refactor-diff-buffer-file-name new))) + (defun refactor-display-edits-as-diff (edits) "Display EDITS as a diff." (with-current-buffer (get-buffer-create "*Refactor Diff*") @@ -302,7 +320,7 @@ argument is the token corresponding to that text replacement.") (let ((refactor-replacement-functions (list (lambda (token) (push token tokens))))) (refactor--apply-replacements reps)) - (diff-no-select buf (current-buffer) nil t diff)) + (refactor-diff buf (buffer-file-name buf) (current-buffer) "*edits*" diff)) (with-current-buffer target (let ((start (point))) (insert-buffer-substring diff) @@ -386,6 +404,12 @@ argument is the token corresponding to that text replacement.") (setq success t)) (funcall (if success #'accept-change-group #'cancel-change-group) change-group)))) +(defun refactor-apply-edits-dtrt (edits) + "If EDITS only affect current buffer, apply them at once; else show diff." + (if (and (eq (car (car edits)) (current-buffer)) (null (cdr edits))) + (refactor-apply-edits-at-once edits) + (refactor-display-edits-as-diff edits))) + ;;;###autoload (defun refactor-apply-edits (edits) "Apply EDITS. -- 2.39.5