branch: new-with-editor commit 8d52f933e50624c7bca3880f57297ac17ba4ac2d Author: Jonas Bernoulli <jo...@bernoul.li> Commit: Jonas Bernoulli <jo...@bernoul.li>
Recognize output of the sleeping editor even if it arrives in chunks Fixes https://github.com/magit/magit/issues/4288#issuecomment-797972932. --- with-editor.el | 54 +++++++++++++++++++++++++++++++++--------------------- 1 file changed, 33 insertions(+), 21 deletions(-) diff --git a/with-editor.el b/with-editor.el index 4a43595..ba856e6 100644 --- a/with-editor.el +++ b/with-editor.el @@ -641,33 +641,45 @@ may not insert the text into the PROCESS's buffer. Then it calls (defvar with-editor-filter-visit-hook nil) +(defconst with-editor-sleeping-editor-regexp + "^WITH-EDITOR: \\([0-9]+\\) OPEN \\([^]+?\\)\\(?: IN \\([^\r]+?\\)\\)?\r?$") + (defun with-editor-output-filter (string) + (with-editor-sleeping-editor-filter nil string)) + +(defun with-editor-sleeping-editor-filter (process string) + (when-let ((incomplete (and process (process-get process 'incomplete)))) + (setq string (concat incomplete string))) (save-match-data - (if (string-match "^WITH-EDITOR: \ -\\([0-9]+\\) OPEN \\([^]+?\\)\ -\\(?: IN \\([^\r]+?\\)\\)?\r?$" string) - (let ((pid (match-string 1 string)) - (file (match-string 2 string)) - (dir (match-string 3 string))) - (unless (file-name-absolute-p file) - (setq file (expand-file-name file dir))) - (when default-directory - (setq file (concat (file-remote-p default-directory) file))) - (with-current-buffer (find-file-noselect file) - (with-editor-mode 1) - (setq with-editor--pid pid) - (run-hooks 'with-editor-filter-visit-hook) - (funcall (or (with-editor-server-window) 'switch-to-buffer) - (current-buffer)) - (kill-local-variable 'server-window)) - nil) - string))) + (cond + ((and process (not (string-match-p "\n\\'" string))) + (process-put process 'incomplete string) + nil) + ((string-match with-editor-sleeping-editor-regexp string) + (when process + (process-put process 'incomplete nil)) + (let ((pid (match-string 1 string)) + (file (match-string 2 string)) + (dir (match-string 3 string))) + (unless (file-name-absolute-p file) + (setq file (expand-file-name file dir))) + (when default-directory + (setq file (concat (file-remote-p default-directory) file))) + (with-current-buffer (find-file-noselect file) + (with-editor-mode 1) + (setq with-editor--pid pid) + (run-hooks 'with-editor-filter-visit-hook) + (funcall (or (with-editor-server-window) 'switch-to-buffer) + (current-buffer)) + (kill-local-variable 'server-window))) + nil) + (t string)))) (defun with-editor-process-filter (process string &optional no-default-filter) "Listen for edit requests by child processes." (let ((default-directory (process-get process 'default-dir))) - (with-editor-output-filter string)) + (with-editor-sleeping-editor-filter process string)) (unless no-default-filter (internal-default-process-filter process string))) @@ -744,7 +756,7 @@ This works in `shell-mode', `term-mode', `eshell-mode' and (defun with-editor-emulate-terminal (process string) "Like `term-emulate-terminal' but also handle edit requests." - (when (with-editor-output-filter string) + (when (with-editor-sleeping-editor-filter process string) (term-emulate-terminal process string))) (defvar with-editor-envvars '("EDITOR" "GIT_EDITOR" "HG_EDITOR"))