From 4e664f62f0123ccdb64584cb8e741e9631209245 Mon Sep 17 00:00:00 2001 From: Eli Zaretskii Date: Mon, 16 Feb 2004 13:59:46 +0000 Subject: [PATCH] Autorevert: Add support for VC controlled files. (eval-when-compile): Defvar dired-directory and vc-mode. (auto-revert-vc-cvs-file-version, auto-revert-vc-buffer-p) (auto-revert-handler-vc): New functions. --- lisp/ChangeLog | 7 ++-- lisp/autorevert.el | 82 +++++++++++++++++++++++++++++++++++++++++----- 2 files changed, 78 insertions(+), 11 deletions(-) diff --git a/lisp/ChangeLog b/lisp/ChangeLog index c13e5dff431..88fa9377f46 100644 --- a/lisp/ChangeLog +++ b/lisp/ChangeLog @@ -5,13 +5,16 @@ 2004-02-16 Jari Aalto - Autorevert: Add support to detect changed dired buffers. + Autorevert: Add support to detect changed dired buffers and for + VC controlled files. * autorevert.el (auto-revert-active-p, auto-revert-list-diff) (auto-revert-dired-file-list, auto-revert-dired-changed-p) (auto-revert-handler, auto-revert-active-p): New functions. (auto-revert-buffers): Moved revert logic to `auto-revert-handler' and `auto-revert-active-p'. - (eval-when-compile): Defvar dired-directory. + (eval-when-compile): Defvar dired-directory and vc-mode. + (auto-revert-vc-cvs-file-version, auto-revert-vc-buffer-p) + (auto-revert-handler-vc): New functions. 2004-02-16 Alfred M. Szmidt (tiny change) diff --git a/lisp/autorevert.el b/lisp/autorevert.el index 309517476e1..a720e547b20 100644 --- a/lisp/autorevert.el +++ b/lisp/autorevert.el @@ -71,9 +71,12 @@ (require 'timer) (autoload 'dired-get-filename "dired") +(autoload 'vc-workfile-version "vc-hooks") +(autoload 'vc-mode-line "vc-hooks") (eval-when-compile (defvar dired-directory) + (defvar vc-mode) (require 'cl)) @@ -294,9 +297,12 @@ Use `auto-revert-mode' to revert a particular buffer." (defun auto-revert-buffer-p () "Check if current buffer should be reverted." - ;; Always include dired buffers to list. It would be too expensive + ;; - Always include dired buffers to list. It would be too expensive ;; to test the "revert" status here each time timer launches. + ;; - Same for VC buffers. (or (eq major-mode 'dired-mode) + (and (not (buffer-modified-p)) + (auto-revert-vc-buffer-p)) (and (not (buffer-modified-p)) (if (buffer-file-name) (and (file-readable-p (buffer-file-name)) @@ -306,23 +312,81 @@ Use `auto-revert-mode' to revert a particular buffer." global-auto-revert-non-file-buffers) auto-revert-mode)))))) +(defun auto-revert-vc-cvs-file-version (file) + "Get version of FILE by reading control file on disk." + (let* ((control "CVS/Entries") + (name (file-name-nondirectory file)) + (path (format "%s/%s" + (file-name-directory file) + control))) + (when (file-exists-p path) + (with-temp-buffer + (insert-file-contents-literally path) + (goto-char (point-min)) + (when (re-search-forward + ;; /file.txt/1.3/Mon Sep 15 18:43:20 2003// + (format "%s/\\([.0-9]+\\)" (regexp-quote name)) + nil t) + (match-string 1)))))) + +(defun auto-revert-vc-buffer-p () + "Check if buffer is version controlled." + (and (boundp 'vc-mode) + (string-match "[0-9]" (or vc-mode "")))) + +(defun auto-revert-handler-vc () + "Check if version controlled buffer needs revert." + ;; [Emacs 1] + ;; 1. File is saved (*) + ;; 2. checkin is done 1.1 -> 1.2 + ;; 3. VC reverts, so that updated version number is shown in mode line + ;; + ;; Suppose the same file has been opened in another Emacs and + ;; autorevert.el is on. + ;; + ;; [Emacs 2] + ;; 1. Step (1) is detected and buffer is reverted. + ;; 2. But check in does not always change the file in dis, but possibly only + ;; control files like CVS/Entries + ;; 3. The buffer is not reverted to update VC version line. + ;; Incorrect version number 1.1 is shown in this Emacs + ;; + (when (featurep 'vc) + (let* ((file (buffer-file-name)) + (backend (vc-backend (buffer-file-name))) + (version-buffer (vc-workfile-version file))) + (when (stringp version-buffer) + (cond + ((eq backend 'CVS) + (let ((version-file + (auto-revert-vc-cvs-file-version (buffer-file-name)))) + (and (stringp version-file) + (not (string-match version-file version-buffer))))) + ((eq backend 'RCS) + ;; TODO: + )))))) + (defun auto-revert-handler () "Revert current buffer." - (let (done) + (let (revert) (cond ((eq major-mode 'dired-mode) ;; Dired includes revert-buffer-function (when (and revert-buffer-function (auto-revert-dired-changed-p)) - (setq done t) - (revert-buffer t t t))) + (setq revert t))) + ((auto-revert-vc-buffer-p) + (when (auto-revert-handler-vc) + (setq revert 'vc))) ((or (buffer-file-name) revert-buffer-function) - (setq done t) - (revert-buffer 'ignore-auto 'dont-ask 'preserve-modes))) - (if (and done - auto-revert-verbose) - (message "Reverting buffer `%s'." (buffer-name))))) + (setq revert t))) + (when revert + (revert-buffer 'ignore-auto 'dont-ask 'preserve-modes) + (if (eq revert 'vc) + (vc-mode-line buffer-file-name)) + (if auto-revert-verbose + (message "Reverting buffer `%s'." (buffer-name)))))) (defun auto-revert-buffers () "Revert buffers as specified by Auto-Revert and Global Auto-Revert Mode. -- 2.39.2