comparison lisp/vc-hg.el @ 81476:3dedb2297b98

(vc-hg-global-switches): Simplify. (vc-hg-state): Handle more states. (vc-hg-diff): Fix doc-string. (vc-hg-register): New function. (vc-hg-checkout): Likewise.
author Dan Nicolaescu <dann@ics.uci.edu>
date Wed, 20 Jun 2007 06:32:42 +0000
parents 51869b1d11fd
children 2d50f85a03de
comparison
equal deleted inserted replaced
81475:d7d688f667ae 81476:3dedb2297b98
1 ;;; vc-hg.el --- VC backend for the mercurial version control system 1 ;;; vc-hg.el --- VC backend for the mercurial version control system
2 2
3 ;; Copyright (C) 2006 Ivan Kanis 3 ;; Copyright (C) 2006, 2007 Free Software Foundation, Inc.
4
4 ;; Author: Ivan Kanis 5 ;; Author: Ivan Kanis
5 ;; $Id: vc-hg.el 1889 2007-06-17 12:39:26Z ivan $ 6 ;; Keywords: tools
7 ;; Version: 1889
6 ;; 8 ;;
7 ;; This program is free software ; you can redistribute it and/or modify 9 ;; This program is free software ; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by 10 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation ; either version 2 of the License, or 11 ;; the Free Software Foundation ; either version 2 of the License, or
10 ;; (at your option) any later version. 12 ;; (at your option) any later version.
20 22
21 ;;; Commentary: 23 ;;; Commentary:
22 24
23 ;; This is a mercurial version control backend 25 ;; This is a mercurial version control backend
24 26
25 ;;; THANKS: 27 ;;; Thanks:
26 28
27 ;;; BUGS: 29 ;;; Bugs:
28 30
29 ;;; INSTALLATION: 31 ;;; Installation:
32
33 ;;; Todo:
34
35 ;; Implement the rest of the vc interface
36
37 ;; Implement Stefan Monnier's advice:
38 ;; vc-hg-registered and vc-hg-state
39 ;; Both of those functions should be super extra careful to fail gracefully in
40 ;; unexpected circumstances. The most important such case is when the `hg'
41 ;; executable is not available. The reason this is important is that any error
42 ;; there will prevent the user from even looking at the file :-(
43 ;; Ideally, just like in vc-arch and vc-cvs, checking that the file is under
44 ;; mercurial's control and extracting the current revision should be done
45 ;; without even using `hg' (this way even if you don't have `hg' installed,
46 ;; Emacs is able to tell you this file is under mercurial's control).
47
48 ;;; History:
49 ;;
30 50
31 ;;; Code: 51 ;;; Code:
32 52
33 (eval-when-compile 53 (eval-when-compile
34 (require 'vc)) 54 (require 'vc))
35 55
36 ;; (setq vc-handled-backends '(CVS SVN hg)) 56 ;; XXX This should be moved to vc-hooks when the full vc interface is
57 ;; implemented.
58 (add-to-list 'vc-handled-backends 'HG)
37 59
38 ;;; Customization options 60 ;;; Customization options
39 61
40 (defcustom vc-hg-global-switches nil 62 (defcustom vc-hg-global-switches nil
41 "*Global switches to pass to any Hg command." 63 "*Global switches to pass to any Hg command."
42 :type '(choice (const :tag "None" nil) 64 :type '(choice (const :tag "None" nil)
43 (string :tag "Argument String") 65 (string :tag "Argument String")
44 (repeat :tag "Argument List" 66 (repeat :tag "Argument List"
45 :value ("") 67 :value ("")
46 string)) 68 string))
47 :version "22.1" 69 ;; :version "22.2"
48 :group 'vc) 70 :group 'vc)
49 71
50 ;;; State querying functions 72 ;;; State querying functions
51 73
74 ;;; Modelled after the similar function in vc-bzr.el
52 (defun vc-hg-registered (file) 75 (defun vc-hg-registered (file)
53 "Return t if FILE is registered in Hg" 76 "Return non-nil if FILE is registered with hg."
54 (if (eq 0 (call-process "hg" nil nil nil 77 (if (vc-find-root file ".hg") ; short cut
55 "--cwd" (file-name-directory file) 78 (vc-hg-state file))) ; expensive
56 "status" (file-name-nondirectory file)))
57 (vc-file-setprop file 'vc-name file) nil))
58 79
59 (defun vc-hg-state (file) 80 (defun vc-hg-state (file)
60 "Return state of files in Hg" 81 "Hg-specific version of `vc-state'."
61 (let ((out (vc-hg-internal-status file))) 82 (let ((out (vc-hg-internal-status file)))
62 (if (eq 0 (length out)) 'up-to-date 83 (if (eq 0 (length out)) 'up-to-date
63 (let ((state (aref out 0))) 84 (let ((state (aref out 0)))
64 (cond 85 (cond
65 ((eq state ?M) 'edited) 86 ((eq state ?M) 'edited)
87 ((eq state ?A) 'edited)
66 ((eq state ?P) 'needs-patch) 88 ((eq state ?P) 'needs-patch)
89 ((eq state ??) nil)
67 (t 'up-to-date)))))) 90 (t 'up-to-date))))))
68 91
69 (defun vc-hg-workfile-version (file) 92 (defun vc-hg-workfile-version (file)
70 "Return version number of file" 93 "Hg-specific version of `vc-workfile-version'."
71 (let ((out (vc-hg-internal-log file))) 94 (let ((out (vc-hg-internal-log file)))
72 (if (string-match "changeset: *\\([0-9]*\\)" out) 95 (if (string-match "changeset: *\\([0-9]*\\)" out)
73 (match-string 1 out) 96 (match-string 1 out)
74 "0"))) 97 "0")))
75
76 (defun vc-hg-internal-log(file)
77 "Return log of FILE"
78 (with-output-to-string
79 (with-current-buffer
80 standard-output
81 (call-process
82 "hg" nil t nil "--cwd" (file-name-directory file)
83 "log" "-l1" (file-name-nondirectory file)))))
84 98
85 ;;; History functions 99 ;;; History functions
86 100
87 (defun vc-hg-print-log(file &optional buffer) 101 (defun vc-hg-print-log(file &optional buffer)
88 "Get change log associated with FILE." 102 "Get change log associated with FILE."
89 (vc-hg-command 103 (vc-hg-command
90 buffer 104 buffer
91 (if (and (vc-stay-local-p file) (fboundp 'start-process)) 'async 0) 105 (if (and (vc-stay-local-p file) (fboundp 'start-process)) 'async 0)
92 file "log")) 106 file "log"))
93 107
94 (defun vc-hg-internal-status(file)
95 "Return status of FILE"
96 (with-output-to-string
97 (with-current-buffer
98 standard-output
99 (call-process
100 "hg" nil t nil "--cwd" (file-name-directory file)
101 "status" (file-name-nondirectory file)))))
102
103 (defun vc-hg-diff (file &optional oldvers newvers buffers) 108 (defun vc-hg-diff (file &optional oldvers newvers buffers)
104 "Get a difference report using hg between two versions of FILE." 109 "Get a difference report using hg between two versions of FILE."
105 (when buffers (message buffers)) 110 (when buffers (message buffers))
106 (unless buffers (setq buffers "*vc-diff*")) 111 (unless buffers (setq buffers "*vc-diff*"))
107 (when oldvers (message oldvers)) 112 (when oldvers (message oldvers))
108 (when newvers (message newvers)) 113 (when newvers (message newvers))
109 (call-process "hg" nil buffers nil 114 (call-process "hg" nil buffers nil
110 "--cwd" (file-name-directory file) 115 "--cwd" (file-name-directory file)
111 "diff" (file-name-nondirectory file))) 116 "diff" (file-name-nondirectory file)))
117
118 (defun vc-hg-register (file &optional rev comment)
119 "Register FILE under hg.
120 REV is ignored.
121 COMMENT is ignored."
122 (vc-hg-command nil nil file "add"))
123
124 ;;; Modelled after the similar function in vc-bzr.el
125 (defun vc-hg-checkout (file &optional editable rev workfile)
126 "Retrieve a revision of FILE into a WORKFILE.
127 EDITABLE is ignored.
128 REV is the revision to check out into WORKFILE."
129 (unless workfile
130 (setq workfile (vc-version-backup-file-name file rev)))
131 (let ((coding-system-for-read 'binary)
132 (coding-system-for-write 'binary))
133 (with-temp-file workfile
134 (if rev
135 (vc-hg-command t nil file "cat" "-r" rev)
136 (vc-hg-command t nil file "cat")))))
137
138 (defun vc-hg-checkout-model (file)
139 'implicit)
112 140
113 ;;; Internal functions 141 ;;; Internal functions
114 142
115 (defun vc-hg-command (buffer okstatus file &rest flags) 143 (defun vc-hg-command (buffer okstatus file &rest flags)
116 "A wrapper around `vc-do-command' for use in vc-hg.el. 144 "A wrapper around `vc-do-command' for use in vc-hg.el.
120 (if (stringp vc-hg-global-switches) 148 (if (stringp vc-hg-global-switches)
121 (cons vc-hg-global-switches flags) 149 (cons vc-hg-global-switches flags)
122 (append vc-hg-global-switches 150 (append vc-hg-global-switches
123 flags)))) 151 flags))))
124 152
153 (defun vc-hg-internal-log (file)
154 "Return log of FILE."
155 (with-output-to-string
156 (with-current-buffer
157 standard-output
158 (call-process
159 "hg" nil t nil "--cwd" (file-name-directory file)
160 "log" "-l1" (file-name-nondirectory file)))))
161
162 (defun vc-hg-internal-status(file)
163 "Return status of FILE."
164 (with-output-to-string
165 (with-current-buffer
166 standard-output
167 (call-process
168 "hg" nil t nil "--cwd" (file-name-directory file)
169 "status" (file-name-nondirectory file)))))
170
125 (provide 'vc-hg) 171 (provide 'vc-hg)
126 172
173 ;;; vc-hg.el ends here