* vc-p4.el (vc-p4-diff): Support lists of files. Perform only a

single request to the server in the simplest case (diff edited
file to synced version).

* p4-lowlevel.el (p4-lowlevel-command-into-buffer): Don't reorder
info and text lines.
(p4-lowlevel-diff): Support lists of files as well as a single file.

[git-p4: depot-paths = "//guest/Ben_Key/vc-p4/,//guest/jonathan_kamens/vc-p4/,//guest/magnus_henoch/vc-p4/": change = 7484]
This commit is contained in:
Magnus Henoch 2009-11-16 12:56:58 -08:00
parent 5305e9d39e
commit 4667f79c0a
2 changed files with 74 additions and 43 deletions

View file

@ -303,9 +303,7 @@ buffer, then puts output in that buffer. Returns the buffer."
(save-excursion (save-excursion
(set-buffer output-buffer) (set-buffer output-buffer)
(erase-buffer) (erase-buffer)
(insert (p4-lowlevel-info-lines output-alist)) (insert (p4-lowlevel-lines-matching-tag "^\\(text\\|info\\)" output-alist))
(if (setq text (p4-lowlevel-text output-alist))
(insert text))
output-buffer))) output-buffer)))
(defun p4-lowlevel-command-messages () (defun p4-lowlevel-command-messages ()
@ -417,19 +415,27 @@ value with `-m'; if S-VAL is non-nil, pass that value with `-s'."
; DO need to support diffing a single file. ; DO need to support diffing a single file.
; Do NOT need to support diffing multiple files. ; Do NOT need to support diffing multiple files.
(defun p4-lowlevel-diff (file &optional rev buffer) (defun p4-lowlevel-diff (files &optional rev buffer)
"Run `p4 diff' on FILE at revision REV and return a buffer "Run `p4 diff' on FILE at revision REV and return a buffer
containing the results. REV is in the syntax described by `p4 help containing the results. REV is in the syntax described by `p4 help
revisions'. If REV is nil, compare the client's sync'd revision to revisions'. If REV is nil, compare the client's sync'd revision to
the file on disk. Uses `p4-lowlevel-diff-switches' to determine flags the file on disk. Uses `p4-lowlevel-diff-switches' to determine flags
to pass to `p4 diff'. If optional BUFFER is non-nil, put output in to pass to `p4 diff'. If optional BUFFER is non-nil, put output in
that buffer." that buffer."
(unless (listp files)
(setq files (list files)))
(setq rev (p4-lowlevel-canonicalize-revision rev)) (setq rev (p4-lowlevel-canonicalize-revision rev))
(when (file-directory-p file) (setq files
(setq file (concat (directory-file-name file) "/..."))) (mapcar (lambda (file)
(let* ((file-spec (if rev (concat file rev) file)) (if (file-directory-p file)
(concat (directory-file-name file) "/...")
file))
files))
(let* ((file-specs (if rev
(mapcar (lambda (file) (concat file rev)) files)
files))
(diff-args (append (list "diff") p4-lowlevel-diff-switches (diff-args (append (list "diff") p4-lowlevel-diff-switches
(list "-f" "-t" file-spec))) (list "-f" "-t") file-specs))
(buffer (p4-lowlevel-command-into-buffer diff-args (buffer (p4-lowlevel-command-into-buffer diff-args
(or buffer "diff")))) (or buffer "diff"))))
buffer)) buffer))

View file

@ -492,43 +492,68 @@ files under the default directory otherwise."
("^date: \\(.+\\)" (1 'change-log-date)) ("^date: \\(.+\\)" (1 'change-log-date))
("^summary:[ \t]+\\(.+\\)" (1 'log-view-message)))))) ("^summary:[ \t]+\\(.+\\)" (1 'log-view-message))))))
(defun vc-p4-diff (files &optional rev1 rev2 buff) (defun vc-p4-diff (file-or-files &optional rev1 rev2 buff)
"Do a Perforce diff." "Do a Perforce diff."
(let* ((buffer (or (bufferp buff) (get-buffer-create "*vc-diff*"))) (let* ((buffer (or (bufferp buff) (get-buffer-create "*vc-diff*")))
;; In emacs-23 vc-diff has a list of files as a parameter, (files (if (atom file-or-files) (list file-or-files) file-or-files))
;; before it used to be just a single file. We don't support (inhibit-read-only t))
;; that interface yet, so just use the first file in the list. (cond
(file (if (listp files) (car files) files)) ((and (null rev1) (null rev2))
(workfile-version (vc-file-getprop file 'vc-workfile-version)) (let (added modified)
(inhibit-read-only t)) (dolist (file files)
(if (not rev1) (if (string= (vc-file-getprop file 'vc-p4-action) "add")
(if (not rev2) (push file added)
(if (string= (vc-file-getprop file 'vc-p4-action) (push file modified)))
"add") (setq added (nreverse added)
; I can't figure out anything better to do here than modified (nreverse modified))
; to use diff-switches. It would be so much easier if
; "p4 diff" and "p4 diff2" accepted real diff ;; For added files, Perforce can't give us what we want
; arguments instead of arguments with "-d" in front of ;; (diff the new file against /dev/null), so we do it
; them. ;; ourselves.
(progn (with-current-buffer buffer
(set-buffer buffer) (erase-buffer)
(erase-buffer) (dolist (file added)
(apply 'call-process (apply 'call-process
(append (append
(list diff-command (list diff-command
nil nil
buffer buffer
nil) nil)
(if (listp diff-switches) (if (listp diff-switches)
diff-switches diff-switches
(list diff-switches)) (list diff-switches))
(list "/dev/null" (list "/dev/null"
file)))) file))))
(p4-lowlevel-diff file nil buffer))
(p4-lowlevel-diff2 file file workfile-version rev2 buffer)) ;; Now diff all the modified files in a single call to the server.
(if rev2 (when modified
(p4-lowlevel-diff2 file file rev1 rev2 buffer) (let (temp-buffer)
(p4-lowlevel-diff file rev1 buffer))))) (unwind-protect
(progn
(setq temp-buffer (p4-lowlevel-diff modified))
(insert-buffer-substring temp-buffer))
(when (buffer-live-p temp-buffer)
(kill-buffer temp-buffer))))))))
(t
;; At this point things get complicated. Let's just make one
;; request per file and hope the server administrator doesn't
;; mind.
(with-current-buffer buffer
(let (temp-buffer)
(dolist (file files)
(setq temp-buffer
(cond
((and (not rev1) rev2)
(p4-lowlevel-diff2 file file
(vc-file-getprop file 'vc-workfile-version)
rev2))
((and rev1 rev2)
(p4-lowlevel-diff2 file file rev1 rev2))
((and rev1 (not rev2))
(p4-lowlevel-diff file rev1))))
(insert-buffer-substring temp-buffer)
(kill-buffer temp-buffer))))))))
(defun vc-p4-annotate-command (file buffer &optional version) (defun vc-p4-annotate-command (file buffer &optional version)
"Annotate FILE into BUFFER file using `vc-p4-annotate-command'. "Annotate FILE into BUFFER file using `vc-p4-annotate-command'.