##// END OF EJS Templates
debugignore: find out if a file is being ignored...
Laurent Charignon -
r27671:067d87fe default
parent child Browse files
Show More
@@ -1,7013 +1,7039 b''
1 # commands.py - command processing for mercurial
1 # commands.py - command processing for mercurial
2 #
2 #
3 # Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
3 # Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
4 #
4 #
5 # This software may be used and distributed according to the terms of the
5 # This software may be used and distributed according to the terms of the
6 # GNU General Public License version 2 or any later version.
6 # GNU General Public License version 2 or any later version.
7
7
8 from node import hex, bin, nullhex, nullid, nullrev, short
8 from node import hex, bin, nullhex, nullid, nullrev, short
9 from lock import release
9 from lock import release
10 from i18n import _
10 from i18n import _
11 import os, re, difflib, time, tempfile, errno, shlex
11 import os, re, difflib, time, tempfile, errno, shlex
12 import sys, socket
12 import sys, socket
13 import hg, scmutil, util, revlog, copies, error, bookmarks
13 import hg, scmutil, util, revlog, copies, error, bookmarks
14 import patch, help, encoding, templatekw, discovery
14 import patch, help, encoding, templatekw, discovery
15 import archival, changegroup, cmdutil, hbisect
15 import archival, changegroup, cmdutil, hbisect
16 import sshserver, hgweb
16 import sshserver, hgweb
17 import extensions
17 import extensions
18 import merge as mergemod
18 import merge as mergemod
19 import minirst, revset, fileset
19 import minirst, revset, fileset
20 import dagparser, context, simplemerge, graphmod, copies
20 import dagparser, context, simplemerge, graphmod, copies
21 import random, operator
21 import random, operator
22 import setdiscovery, treediscovery, dagutil, pvec, localrepo, destutil
22 import setdiscovery, treediscovery, dagutil, pvec, localrepo, destutil
23 import phases, obsolete, exchange, bundle2, repair, lock as lockmod
23 import phases, obsolete, exchange, bundle2, repair, lock as lockmod
24 import ui as uimod
24 import ui as uimod
25 import streamclone
25 import streamclone
26 import commandserver
26 import commandserver
27
27
28 table = {}
28 table = {}
29
29
30 command = cmdutil.command(table)
30 command = cmdutil.command(table)
31
31
32 # Space delimited list of commands that don't require local repositories.
32 # Space delimited list of commands that don't require local repositories.
33 # This should be populated by passing norepo=True into the @command decorator.
33 # This should be populated by passing norepo=True into the @command decorator.
34 norepo = ''
34 norepo = ''
35 # Space delimited list of commands that optionally require local repositories.
35 # Space delimited list of commands that optionally require local repositories.
36 # This should be populated by passing optionalrepo=True into the @command
36 # This should be populated by passing optionalrepo=True into the @command
37 # decorator.
37 # decorator.
38 optionalrepo = ''
38 optionalrepo = ''
39 # Space delimited list of commands that will examine arguments looking for
39 # Space delimited list of commands that will examine arguments looking for
40 # a repository. This should be populated by passing inferrepo=True into the
40 # a repository. This should be populated by passing inferrepo=True into the
41 # @command decorator.
41 # @command decorator.
42 inferrepo = ''
42 inferrepo = ''
43
43
44 # label constants
44 # label constants
45 # until 3.5, bookmarks.current was the advertised name, not
45 # until 3.5, bookmarks.current was the advertised name, not
46 # bookmarks.active, so we must use both to avoid breaking old
46 # bookmarks.active, so we must use both to avoid breaking old
47 # custom styles
47 # custom styles
48 activebookmarklabel = 'bookmarks.active bookmarks.current'
48 activebookmarklabel = 'bookmarks.active bookmarks.current'
49
49
50 # common command options
50 # common command options
51
51
52 globalopts = [
52 globalopts = [
53 ('R', 'repository', '',
53 ('R', 'repository', '',
54 _('repository root directory or name of overlay bundle file'),
54 _('repository root directory or name of overlay bundle file'),
55 _('REPO')),
55 _('REPO')),
56 ('', 'cwd', '',
56 ('', 'cwd', '',
57 _('change working directory'), _('DIR')),
57 _('change working directory'), _('DIR')),
58 ('y', 'noninteractive', None,
58 ('y', 'noninteractive', None,
59 _('do not prompt, automatically pick the first choice for all prompts')),
59 _('do not prompt, automatically pick the first choice for all prompts')),
60 ('q', 'quiet', None, _('suppress output')),
60 ('q', 'quiet', None, _('suppress output')),
61 ('v', 'verbose', None, _('enable additional output')),
61 ('v', 'verbose', None, _('enable additional output')),
62 ('', 'config', [],
62 ('', 'config', [],
63 _('set/override config option (use \'section.name=value\')'),
63 _('set/override config option (use \'section.name=value\')'),
64 _('CONFIG')),
64 _('CONFIG')),
65 ('', 'debug', None, _('enable debugging output')),
65 ('', 'debug', None, _('enable debugging output')),
66 ('', 'debugger', None, _('start debugger')),
66 ('', 'debugger', None, _('start debugger')),
67 ('', 'encoding', encoding.encoding, _('set the charset encoding'),
67 ('', 'encoding', encoding.encoding, _('set the charset encoding'),
68 _('ENCODE')),
68 _('ENCODE')),
69 ('', 'encodingmode', encoding.encodingmode,
69 ('', 'encodingmode', encoding.encodingmode,
70 _('set the charset encoding mode'), _('MODE')),
70 _('set the charset encoding mode'), _('MODE')),
71 ('', 'traceback', None, _('always print a traceback on exception')),
71 ('', 'traceback', None, _('always print a traceback on exception')),
72 ('', 'time', None, _('time how long the command takes')),
72 ('', 'time', None, _('time how long the command takes')),
73 ('', 'profile', None, _('print command execution profile')),
73 ('', 'profile', None, _('print command execution profile')),
74 ('', 'version', None, _('output version information and exit')),
74 ('', 'version', None, _('output version information and exit')),
75 ('h', 'help', None, _('display help and exit')),
75 ('h', 'help', None, _('display help and exit')),
76 ('', 'hidden', False, _('consider hidden changesets')),
76 ('', 'hidden', False, _('consider hidden changesets')),
77 ]
77 ]
78
78
79 dryrunopts = [('n', 'dry-run', None,
79 dryrunopts = [('n', 'dry-run', None,
80 _('do not perform actions, just print output'))]
80 _('do not perform actions, just print output'))]
81
81
82 remoteopts = [
82 remoteopts = [
83 ('e', 'ssh', '',
83 ('e', 'ssh', '',
84 _('specify ssh command to use'), _('CMD')),
84 _('specify ssh command to use'), _('CMD')),
85 ('', 'remotecmd', '',
85 ('', 'remotecmd', '',
86 _('specify hg command to run on the remote side'), _('CMD')),
86 _('specify hg command to run on the remote side'), _('CMD')),
87 ('', 'insecure', None,
87 ('', 'insecure', None,
88 _('do not verify server certificate (ignoring web.cacerts config)')),
88 _('do not verify server certificate (ignoring web.cacerts config)')),
89 ]
89 ]
90
90
91 walkopts = [
91 walkopts = [
92 ('I', 'include', [],
92 ('I', 'include', [],
93 _('include names matching the given patterns'), _('PATTERN')),
93 _('include names matching the given patterns'), _('PATTERN')),
94 ('X', 'exclude', [],
94 ('X', 'exclude', [],
95 _('exclude names matching the given patterns'), _('PATTERN')),
95 _('exclude names matching the given patterns'), _('PATTERN')),
96 ]
96 ]
97
97
98 commitopts = [
98 commitopts = [
99 ('m', 'message', '',
99 ('m', 'message', '',
100 _('use text as commit message'), _('TEXT')),
100 _('use text as commit message'), _('TEXT')),
101 ('l', 'logfile', '',
101 ('l', 'logfile', '',
102 _('read commit message from file'), _('FILE')),
102 _('read commit message from file'), _('FILE')),
103 ]
103 ]
104
104
105 commitopts2 = [
105 commitopts2 = [
106 ('d', 'date', '',
106 ('d', 'date', '',
107 _('record the specified date as commit date'), _('DATE')),
107 _('record the specified date as commit date'), _('DATE')),
108 ('u', 'user', '',
108 ('u', 'user', '',
109 _('record the specified user as committer'), _('USER')),
109 _('record the specified user as committer'), _('USER')),
110 ]
110 ]
111
111
112 # hidden for now
112 # hidden for now
113 formatteropts = [
113 formatteropts = [
114 ('T', 'template', '',
114 ('T', 'template', '',
115 _('display with template (EXPERIMENTAL)'), _('TEMPLATE')),
115 _('display with template (EXPERIMENTAL)'), _('TEMPLATE')),
116 ]
116 ]
117
117
118 templateopts = [
118 templateopts = [
119 ('', 'style', '',
119 ('', 'style', '',
120 _('display using template map file (DEPRECATED)'), _('STYLE')),
120 _('display using template map file (DEPRECATED)'), _('STYLE')),
121 ('T', 'template', '',
121 ('T', 'template', '',
122 _('display with template'), _('TEMPLATE')),
122 _('display with template'), _('TEMPLATE')),
123 ]
123 ]
124
124
125 logopts = [
125 logopts = [
126 ('p', 'patch', None, _('show patch')),
126 ('p', 'patch', None, _('show patch')),
127 ('g', 'git', None, _('use git extended diff format')),
127 ('g', 'git', None, _('use git extended diff format')),
128 ('l', 'limit', '',
128 ('l', 'limit', '',
129 _('limit number of changes displayed'), _('NUM')),
129 _('limit number of changes displayed'), _('NUM')),
130 ('M', 'no-merges', None, _('do not show merges')),
130 ('M', 'no-merges', None, _('do not show merges')),
131 ('', 'stat', None, _('output diffstat-style summary of changes')),
131 ('', 'stat', None, _('output diffstat-style summary of changes')),
132 ('G', 'graph', None, _("show the revision DAG")),
132 ('G', 'graph', None, _("show the revision DAG")),
133 ] + templateopts
133 ] + templateopts
134
134
135 diffopts = [
135 diffopts = [
136 ('a', 'text', None, _('treat all files as text')),
136 ('a', 'text', None, _('treat all files as text')),
137 ('g', 'git', None, _('use git extended diff format')),
137 ('g', 'git', None, _('use git extended diff format')),
138 ('', 'nodates', None, _('omit dates from diff headers'))
138 ('', 'nodates', None, _('omit dates from diff headers'))
139 ]
139 ]
140
140
141 diffwsopts = [
141 diffwsopts = [
142 ('w', 'ignore-all-space', None,
142 ('w', 'ignore-all-space', None,
143 _('ignore white space when comparing lines')),
143 _('ignore white space when comparing lines')),
144 ('b', 'ignore-space-change', None,
144 ('b', 'ignore-space-change', None,
145 _('ignore changes in the amount of white space')),
145 _('ignore changes in the amount of white space')),
146 ('B', 'ignore-blank-lines', None,
146 ('B', 'ignore-blank-lines', None,
147 _('ignore changes whose lines are all blank')),
147 _('ignore changes whose lines are all blank')),
148 ]
148 ]
149
149
150 diffopts2 = [
150 diffopts2 = [
151 ('', 'noprefix', None, _('omit a/ and b/ prefixes from filenames')),
151 ('', 'noprefix', None, _('omit a/ and b/ prefixes from filenames')),
152 ('p', 'show-function', None, _('show which function each change is in')),
152 ('p', 'show-function', None, _('show which function each change is in')),
153 ('', 'reverse', None, _('produce a diff that undoes the changes')),
153 ('', 'reverse', None, _('produce a diff that undoes the changes')),
154 ] + diffwsopts + [
154 ] + diffwsopts + [
155 ('U', 'unified', '',
155 ('U', 'unified', '',
156 _('number of lines of context to show'), _('NUM')),
156 _('number of lines of context to show'), _('NUM')),
157 ('', 'stat', None, _('output diffstat-style summary of changes')),
157 ('', 'stat', None, _('output diffstat-style summary of changes')),
158 ('', 'root', '', _('produce diffs relative to subdirectory'), _('DIR')),
158 ('', 'root', '', _('produce diffs relative to subdirectory'), _('DIR')),
159 ]
159 ]
160
160
161 mergetoolopts = [
161 mergetoolopts = [
162 ('t', 'tool', '', _('specify merge tool')),
162 ('t', 'tool', '', _('specify merge tool')),
163 ]
163 ]
164
164
165 similarityopts = [
165 similarityopts = [
166 ('s', 'similarity', '',
166 ('s', 'similarity', '',
167 _('guess renamed files by similarity (0<=s<=100)'), _('SIMILARITY'))
167 _('guess renamed files by similarity (0<=s<=100)'), _('SIMILARITY'))
168 ]
168 ]
169
169
170 subrepoopts = [
170 subrepoopts = [
171 ('S', 'subrepos', None,
171 ('S', 'subrepos', None,
172 _('recurse into subrepositories'))
172 _('recurse into subrepositories'))
173 ]
173 ]
174
174
175 debugrevlogopts = [
175 debugrevlogopts = [
176 ('c', 'changelog', False, _('open changelog')),
176 ('c', 'changelog', False, _('open changelog')),
177 ('m', 'manifest', False, _('open manifest')),
177 ('m', 'manifest', False, _('open manifest')),
178 ('', 'dir', False, _('open directory manifest')),
178 ('', 'dir', False, _('open directory manifest')),
179 ]
179 ]
180
180
181 # Commands start here, listed alphabetically
181 # Commands start here, listed alphabetically
182
182
183 @command('^add',
183 @command('^add',
184 walkopts + subrepoopts + dryrunopts,
184 walkopts + subrepoopts + dryrunopts,
185 _('[OPTION]... [FILE]...'),
185 _('[OPTION]... [FILE]...'),
186 inferrepo=True)
186 inferrepo=True)
187 def add(ui, repo, *pats, **opts):
187 def add(ui, repo, *pats, **opts):
188 """add the specified files on the next commit
188 """add the specified files on the next commit
189
189
190 Schedule files to be version controlled and added to the
190 Schedule files to be version controlled and added to the
191 repository.
191 repository.
192
192
193 The files will be added to the repository at the next commit. To
193 The files will be added to the repository at the next commit. To
194 undo an add before that, see :hg:`forget`.
194 undo an add before that, see :hg:`forget`.
195
195
196 If no names are given, add all files to the repository (except
196 If no names are given, add all files to the repository (except
197 files matching ``.hgignore``).
197 files matching ``.hgignore``).
198
198
199 .. container:: verbose
199 .. container:: verbose
200
200
201 Examples:
201 Examples:
202
202
203 - New (unknown) files are added
203 - New (unknown) files are added
204 automatically by :hg:`add`::
204 automatically by :hg:`add`::
205
205
206 $ ls
206 $ ls
207 foo.c
207 foo.c
208 $ hg status
208 $ hg status
209 ? foo.c
209 ? foo.c
210 $ hg add
210 $ hg add
211 adding foo.c
211 adding foo.c
212 $ hg status
212 $ hg status
213 A foo.c
213 A foo.c
214
214
215 - Specific files to be added can be specified::
215 - Specific files to be added can be specified::
216
216
217 $ ls
217 $ ls
218 bar.c foo.c
218 bar.c foo.c
219 $ hg status
219 $ hg status
220 ? bar.c
220 ? bar.c
221 ? foo.c
221 ? foo.c
222 $ hg add bar.c
222 $ hg add bar.c
223 $ hg status
223 $ hg status
224 A bar.c
224 A bar.c
225 ? foo.c
225 ? foo.c
226
226
227 Returns 0 if all files are successfully added.
227 Returns 0 if all files are successfully added.
228 """
228 """
229
229
230 m = scmutil.match(repo[None], pats, opts)
230 m = scmutil.match(repo[None], pats, opts)
231 rejected = cmdutil.add(ui, repo, m, "", False, **opts)
231 rejected = cmdutil.add(ui, repo, m, "", False, **opts)
232 return rejected and 1 or 0
232 return rejected and 1 or 0
233
233
234 @command('addremove',
234 @command('addremove',
235 similarityopts + subrepoopts + walkopts + dryrunopts,
235 similarityopts + subrepoopts + walkopts + dryrunopts,
236 _('[OPTION]... [FILE]...'),
236 _('[OPTION]... [FILE]...'),
237 inferrepo=True)
237 inferrepo=True)
238 def addremove(ui, repo, *pats, **opts):
238 def addremove(ui, repo, *pats, **opts):
239 """add all new files, delete all missing files
239 """add all new files, delete all missing files
240
240
241 Add all new files and remove all missing files from the
241 Add all new files and remove all missing files from the
242 repository.
242 repository.
243
243
244 Unless names are given, new files are ignored if they match any of
244 Unless names are given, new files are ignored if they match any of
245 the patterns in ``.hgignore``. As with add, these changes take
245 the patterns in ``.hgignore``. As with add, these changes take
246 effect at the next commit.
246 effect at the next commit.
247
247
248 Use the -s/--similarity option to detect renamed files. This
248 Use the -s/--similarity option to detect renamed files. This
249 option takes a percentage between 0 (disabled) and 100 (files must
249 option takes a percentage between 0 (disabled) and 100 (files must
250 be identical) as its parameter. With a parameter greater than 0,
250 be identical) as its parameter. With a parameter greater than 0,
251 this compares every removed file with every added file and records
251 this compares every removed file with every added file and records
252 those similar enough as renames. Detecting renamed files this way
252 those similar enough as renames. Detecting renamed files this way
253 can be expensive. After using this option, :hg:`status -C` can be
253 can be expensive. After using this option, :hg:`status -C` can be
254 used to check which files were identified as moved or renamed. If
254 used to check which files were identified as moved or renamed. If
255 not specified, -s/--similarity defaults to 100 and only renames of
255 not specified, -s/--similarity defaults to 100 and only renames of
256 identical files are detected.
256 identical files are detected.
257
257
258 .. container:: verbose
258 .. container:: verbose
259
259
260 Examples:
260 Examples:
261
261
262 - A number of files (bar.c and foo.c) are new,
262 - A number of files (bar.c and foo.c) are new,
263 while foobar.c has been removed (without using :hg:`remove`)
263 while foobar.c has been removed (without using :hg:`remove`)
264 from the repository::
264 from the repository::
265
265
266 $ ls
266 $ ls
267 bar.c foo.c
267 bar.c foo.c
268 $ hg status
268 $ hg status
269 ! foobar.c
269 ! foobar.c
270 ? bar.c
270 ? bar.c
271 ? foo.c
271 ? foo.c
272 $ hg addremove
272 $ hg addremove
273 adding bar.c
273 adding bar.c
274 adding foo.c
274 adding foo.c
275 removing foobar.c
275 removing foobar.c
276 $ hg status
276 $ hg status
277 A bar.c
277 A bar.c
278 A foo.c
278 A foo.c
279 R foobar.c
279 R foobar.c
280
280
281 - A file foobar.c was moved to foo.c without using :hg:`rename`.
281 - A file foobar.c was moved to foo.c without using :hg:`rename`.
282 Afterwards, it was edited slightly::
282 Afterwards, it was edited slightly::
283
283
284 $ ls
284 $ ls
285 foo.c
285 foo.c
286 $ hg status
286 $ hg status
287 ! foobar.c
287 ! foobar.c
288 ? foo.c
288 ? foo.c
289 $ hg addremove --similarity 90
289 $ hg addremove --similarity 90
290 removing foobar.c
290 removing foobar.c
291 adding foo.c
291 adding foo.c
292 recording removal of foobar.c as rename to foo.c (94% similar)
292 recording removal of foobar.c as rename to foo.c (94% similar)
293 $ hg status -C
293 $ hg status -C
294 A foo.c
294 A foo.c
295 foobar.c
295 foobar.c
296 R foobar.c
296 R foobar.c
297
297
298 Returns 0 if all files are successfully added.
298 Returns 0 if all files are successfully added.
299 """
299 """
300 try:
300 try:
301 sim = float(opts.get('similarity') or 100)
301 sim = float(opts.get('similarity') or 100)
302 except ValueError:
302 except ValueError:
303 raise error.Abort(_('similarity must be a number'))
303 raise error.Abort(_('similarity must be a number'))
304 if sim < 0 or sim > 100:
304 if sim < 0 or sim > 100:
305 raise error.Abort(_('similarity must be between 0 and 100'))
305 raise error.Abort(_('similarity must be between 0 and 100'))
306 matcher = scmutil.match(repo[None], pats, opts)
306 matcher = scmutil.match(repo[None], pats, opts)
307 return scmutil.addremove(repo, matcher, "", opts, similarity=sim / 100.0)
307 return scmutil.addremove(repo, matcher, "", opts, similarity=sim / 100.0)
308
308
309 @command('^annotate|blame',
309 @command('^annotate|blame',
310 [('r', 'rev', '', _('annotate the specified revision'), _('REV')),
310 [('r', 'rev', '', _('annotate the specified revision'), _('REV')),
311 ('', 'follow', None,
311 ('', 'follow', None,
312 _('follow copies/renames and list the filename (DEPRECATED)')),
312 _('follow copies/renames and list the filename (DEPRECATED)')),
313 ('', 'no-follow', None, _("don't follow copies and renames")),
313 ('', 'no-follow', None, _("don't follow copies and renames")),
314 ('a', 'text', None, _('treat all files as text')),
314 ('a', 'text', None, _('treat all files as text')),
315 ('u', 'user', None, _('list the author (long with -v)')),
315 ('u', 'user', None, _('list the author (long with -v)')),
316 ('f', 'file', None, _('list the filename')),
316 ('f', 'file', None, _('list the filename')),
317 ('d', 'date', None, _('list the date (short with -q)')),
317 ('d', 'date', None, _('list the date (short with -q)')),
318 ('n', 'number', None, _('list the revision number (default)')),
318 ('n', 'number', None, _('list the revision number (default)')),
319 ('c', 'changeset', None, _('list the changeset')),
319 ('c', 'changeset', None, _('list the changeset')),
320 ('l', 'line-number', None, _('show line number at the first appearance'))
320 ('l', 'line-number', None, _('show line number at the first appearance'))
321 ] + diffwsopts + walkopts + formatteropts,
321 ] + diffwsopts + walkopts + formatteropts,
322 _('[-r REV] [-f] [-a] [-u] [-d] [-n] [-c] [-l] FILE...'),
322 _('[-r REV] [-f] [-a] [-u] [-d] [-n] [-c] [-l] FILE...'),
323 inferrepo=True)
323 inferrepo=True)
324 def annotate(ui, repo, *pats, **opts):
324 def annotate(ui, repo, *pats, **opts):
325 """show changeset information by line for each file
325 """show changeset information by line for each file
326
326
327 List changes in files, showing the revision id responsible for
327 List changes in files, showing the revision id responsible for
328 each line.
328 each line.
329
329
330 This command is useful for discovering when a change was made and
330 This command is useful for discovering when a change was made and
331 by whom.
331 by whom.
332
332
333 If you include --file, --user, or --date, the revision number is
333 If you include --file, --user, or --date, the revision number is
334 suppressed unless you also include --number.
334 suppressed unless you also include --number.
335
335
336 Without the -a/--text option, annotate will avoid processing files
336 Without the -a/--text option, annotate will avoid processing files
337 it detects as binary. With -a, annotate will annotate the file
337 it detects as binary. With -a, annotate will annotate the file
338 anyway, although the results will probably be neither useful
338 anyway, although the results will probably be neither useful
339 nor desirable.
339 nor desirable.
340
340
341 Returns 0 on success.
341 Returns 0 on success.
342 """
342 """
343 if not pats:
343 if not pats:
344 raise error.Abort(_('at least one filename or pattern is required'))
344 raise error.Abort(_('at least one filename or pattern is required'))
345
345
346 if opts.get('follow'):
346 if opts.get('follow'):
347 # --follow is deprecated and now just an alias for -f/--file
347 # --follow is deprecated and now just an alias for -f/--file
348 # to mimic the behavior of Mercurial before version 1.5
348 # to mimic the behavior of Mercurial before version 1.5
349 opts['file'] = True
349 opts['file'] = True
350
350
351 ctx = scmutil.revsingle(repo, opts.get('rev'))
351 ctx = scmutil.revsingle(repo, opts.get('rev'))
352
352
353 fm = ui.formatter('annotate', opts)
353 fm = ui.formatter('annotate', opts)
354 if ui.quiet:
354 if ui.quiet:
355 datefunc = util.shortdate
355 datefunc = util.shortdate
356 else:
356 else:
357 datefunc = util.datestr
357 datefunc = util.datestr
358 if ctx.rev() is None:
358 if ctx.rev() is None:
359 def hexfn(node):
359 def hexfn(node):
360 if node is None:
360 if node is None:
361 return None
361 return None
362 else:
362 else:
363 return fm.hexfunc(node)
363 return fm.hexfunc(node)
364 if opts.get('changeset'):
364 if opts.get('changeset'):
365 # omit "+" suffix which is appended to node hex
365 # omit "+" suffix which is appended to node hex
366 def formatrev(rev):
366 def formatrev(rev):
367 if rev is None:
367 if rev is None:
368 return '%d' % ctx.p1().rev()
368 return '%d' % ctx.p1().rev()
369 else:
369 else:
370 return '%d' % rev
370 return '%d' % rev
371 else:
371 else:
372 def formatrev(rev):
372 def formatrev(rev):
373 if rev is None:
373 if rev is None:
374 return '%d+' % ctx.p1().rev()
374 return '%d+' % ctx.p1().rev()
375 else:
375 else:
376 return '%d ' % rev
376 return '%d ' % rev
377 def formathex(hex):
377 def formathex(hex):
378 if hex is None:
378 if hex is None:
379 return '%s+' % fm.hexfunc(ctx.p1().node())
379 return '%s+' % fm.hexfunc(ctx.p1().node())
380 else:
380 else:
381 return '%s ' % hex
381 return '%s ' % hex
382 else:
382 else:
383 hexfn = fm.hexfunc
383 hexfn = fm.hexfunc
384 formatrev = formathex = str
384 formatrev = formathex = str
385
385
386 opmap = [('user', ' ', lambda x: x[0].user(), ui.shortuser),
386 opmap = [('user', ' ', lambda x: x[0].user(), ui.shortuser),
387 ('number', ' ', lambda x: x[0].rev(), formatrev),
387 ('number', ' ', lambda x: x[0].rev(), formatrev),
388 ('changeset', ' ', lambda x: hexfn(x[0].node()), formathex),
388 ('changeset', ' ', lambda x: hexfn(x[0].node()), formathex),
389 ('date', ' ', lambda x: x[0].date(), util.cachefunc(datefunc)),
389 ('date', ' ', lambda x: x[0].date(), util.cachefunc(datefunc)),
390 ('file', ' ', lambda x: x[0].path(), str),
390 ('file', ' ', lambda x: x[0].path(), str),
391 ('line_number', ':', lambda x: x[1], str),
391 ('line_number', ':', lambda x: x[1], str),
392 ]
392 ]
393 fieldnamemap = {'number': 'rev', 'changeset': 'node'}
393 fieldnamemap = {'number': 'rev', 'changeset': 'node'}
394
394
395 if (not opts.get('user') and not opts.get('changeset')
395 if (not opts.get('user') and not opts.get('changeset')
396 and not opts.get('date') and not opts.get('file')):
396 and not opts.get('date') and not opts.get('file')):
397 opts['number'] = True
397 opts['number'] = True
398
398
399 linenumber = opts.get('line_number') is not None
399 linenumber = opts.get('line_number') is not None
400 if linenumber and (not opts.get('changeset')) and (not opts.get('number')):
400 if linenumber and (not opts.get('changeset')) and (not opts.get('number')):
401 raise error.Abort(_('at least one of -n/-c is required for -l'))
401 raise error.Abort(_('at least one of -n/-c is required for -l'))
402
402
403 if fm:
403 if fm:
404 def makefunc(get, fmt):
404 def makefunc(get, fmt):
405 return get
405 return get
406 else:
406 else:
407 def makefunc(get, fmt):
407 def makefunc(get, fmt):
408 return lambda x: fmt(get(x))
408 return lambda x: fmt(get(x))
409 funcmap = [(makefunc(get, fmt), sep) for op, sep, get, fmt in opmap
409 funcmap = [(makefunc(get, fmt), sep) for op, sep, get, fmt in opmap
410 if opts.get(op)]
410 if opts.get(op)]
411 funcmap[0] = (funcmap[0][0], '') # no separator in front of first column
411 funcmap[0] = (funcmap[0][0], '') # no separator in front of first column
412 fields = ' '.join(fieldnamemap.get(op, op) for op, sep, get, fmt in opmap
412 fields = ' '.join(fieldnamemap.get(op, op) for op, sep, get, fmt in opmap
413 if opts.get(op))
413 if opts.get(op))
414
414
415 def bad(x, y):
415 def bad(x, y):
416 raise error.Abort("%s: %s" % (x, y))
416 raise error.Abort("%s: %s" % (x, y))
417
417
418 m = scmutil.match(ctx, pats, opts, badfn=bad)
418 m = scmutil.match(ctx, pats, opts, badfn=bad)
419
419
420 follow = not opts.get('no_follow')
420 follow = not opts.get('no_follow')
421 diffopts = patch.difffeatureopts(ui, opts, section='annotate',
421 diffopts = patch.difffeatureopts(ui, opts, section='annotate',
422 whitespace=True)
422 whitespace=True)
423 for abs in ctx.walk(m):
423 for abs in ctx.walk(m):
424 fctx = ctx[abs]
424 fctx = ctx[abs]
425 if not opts.get('text') and util.binary(fctx.data()):
425 if not opts.get('text') and util.binary(fctx.data()):
426 fm.plain(_("%s: binary file\n") % ((pats and m.rel(abs)) or abs))
426 fm.plain(_("%s: binary file\n") % ((pats and m.rel(abs)) or abs))
427 continue
427 continue
428
428
429 lines = fctx.annotate(follow=follow, linenumber=linenumber,
429 lines = fctx.annotate(follow=follow, linenumber=linenumber,
430 diffopts=diffopts)
430 diffopts=diffopts)
431 formats = []
431 formats = []
432 pieces = []
432 pieces = []
433
433
434 for f, sep in funcmap:
434 for f, sep in funcmap:
435 l = [f(n) for n, dummy in lines]
435 l = [f(n) for n, dummy in lines]
436 if l:
436 if l:
437 if fm:
437 if fm:
438 formats.append(['%s' for x in l])
438 formats.append(['%s' for x in l])
439 else:
439 else:
440 sizes = [encoding.colwidth(x) for x in l]
440 sizes = [encoding.colwidth(x) for x in l]
441 ml = max(sizes)
441 ml = max(sizes)
442 formats.append([sep + ' ' * (ml - w) + '%s' for w in sizes])
442 formats.append([sep + ' ' * (ml - w) + '%s' for w in sizes])
443 pieces.append(l)
443 pieces.append(l)
444
444
445 for f, p, l in zip(zip(*formats), zip(*pieces), lines):
445 for f, p, l in zip(zip(*formats), zip(*pieces), lines):
446 fm.startitem()
446 fm.startitem()
447 fm.write(fields, "".join(f), *p)
447 fm.write(fields, "".join(f), *p)
448 fm.write('line', ": %s", l[1])
448 fm.write('line', ": %s", l[1])
449
449
450 if lines and not lines[-1][1].endswith('\n'):
450 if lines and not lines[-1][1].endswith('\n'):
451 fm.plain('\n')
451 fm.plain('\n')
452
452
453 fm.end()
453 fm.end()
454
454
455 @command('archive',
455 @command('archive',
456 [('', 'no-decode', None, _('do not pass files through decoders')),
456 [('', 'no-decode', None, _('do not pass files through decoders')),
457 ('p', 'prefix', '', _('directory prefix for files in archive'),
457 ('p', 'prefix', '', _('directory prefix for files in archive'),
458 _('PREFIX')),
458 _('PREFIX')),
459 ('r', 'rev', '', _('revision to distribute'), _('REV')),
459 ('r', 'rev', '', _('revision to distribute'), _('REV')),
460 ('t', 'type', '', _('type of distribution to create'), _('TYPE')),
460 ('t', 'type', '', _('type of distribution to create'), _('TYPE')),
461 ] + subrepoopts + walkopts,
461 ] + subrepoopts + walkopts,
462 _('[OPTION]... DEST'))
462 _('[OPTION]... DEST'))
463 def archive(ui, repo, dest, **opts):
463 def archive(ui, repo, dest, **opts):
464 '''create an unversioned archive of a repository revision
464 '''create an unversioned archive of a repository revision
465
465
466 By default, the revision used is the parent of the working
466 By default, the revision used is the parent of the working
467 directory; use -r/--rev to specify a different revision.
467 directory; use -r/--rev to specify a different revision.
468
468
469 The archive type is automatically detected based on file
469 The archive type is automatically detected based on file
470 extension (to override, use -t/--type).
470 extension (to override, use -t/--type).
471
471
472 .. container:: verbose
472 .. container:: verbose
473
473
474 Examples:
474 Examples:
475
475
476 - create a zip file containing the 1.0 release::
476 - create a zip file containing the 1.0 release::
477
477
478 hg archive -r 1.0 project-1.0.zip
478 hg archive -r 1.0 project-1.0.zip
479
479
480 - create a tarball excluding .hg files::
480 - create a tarball excluding .hg files::
481
481
482 hg archive project.tar.gz -X ".hg*"
482 hg archive project.tar.gz -X ".hg*"
483
483
484 Valid types are:
484 Valid types are:
485
485
486 :``files``: a directory full of files (default)
486 :``files``: a directory full of files (default)
487 :``tar``: tar archive, uncompressed
487 :``tar``: tar archive, uncompressed
488 :``tbz2``: tar archive, compressed using bzip2
488 :``tbz2``: tar archive, compressed using bzip2
489 :``tgz``: tar archive, compressed using gzip
489 :``tgz``: tar archive, compressed using gzip
490 :``uzip``: zip archive, uncompressed
490 :``uzip``: zip archive, uncompressed
491 :``zip``: zip archive, compressed using deflate
491 :``zip``: zip archive, compressed using deflate
492
492
493 The exact name of the destination archive or directory is given
493 The exact name of the destination archive or directory is given
494 using a format string; see :hg:`help export` for details.
494 using a format string; see :hg:`help export` for details.
495
495
496 Each member added to an archive file has a directory prefix
496 Each member added to an archive file has a directory prefix
497 prepended. Use -p/--prefix to specify a format string for the
497 prepended. Use -p/--prefix to specify a format string for the
498 prefix. The default is the basename of the archive, with suffixes
498 prefix. The default is the basename of the archive, with suffixes
499 removed.
499 removed.
500
500
501 Returns 0 on success.
501 Returns 0 on success.
502 '''
502 '''
503
503
504 ctx = scmutil.revsingle(repo, opts.get('rev'))
504 ctx = scmutil.revsingle(repo, opts.get('rev'))
505 if not ctx:
505 if not ctx:
506 raise error.Abort(_('no working directory: please specify a revision'))
506 raise error.Abort(_('no working directory: please specify a revision'))
507 node = ctx.node()
507 node = ctx.node()
508 dest = cmdutil.makefilename(repo, dest, node)
508 dest = cmdutil.makefilename(repo, dest, node)
509 if os.path.realpath(dest) == repo.root:
509 if os.path.realpath(dest) == repo.root:
510 raise error.Abort(_('repository root cannot be destination'))
510 raise error.Abort(_('repository root cannot be destination'))
511
511
512 kind = opts.get('type') or archival.guesskind(dest) or 'files'
512 kind = opts.get('type') or archival.guesskind(dest) or 'files'
513 prefix = opts.get('prefix')
513 prefix = opts.get('prefix')
514
514
515 if dest == '-':
515 if dest == '-':
516 if kind == 'files':
516 if kind == 'files':
517 raise error.Abort(_('cannot archive plain files to stdout'))
517 raise error.Abort(_('cannot archive plain files to stdout'))
518 dest = cmdutil.makefileobj(repo, dest)
518 dest = cmdutil.makefileobj(repo, dest)
519 if not prefix:
519 if not prefix:
520 prefix = os.path.basename(repo.root) + '-%h'
520 prefix = os.path.basename(repo.root) + '-%h'
521
521
522 prefix = cmdutil.makefilename(repo, prefix, node)
522 prefix = cmdutil.makefilename(repo, prefix, node)
523 matchfn = scmutil.match(ctx, [], opts)
523 matchfn = scmutil.match(ctx, [], opts)
524 archival.archive(repo, dest, node, kind, not opts.get('no_decode'),
524 archival.archive(repo, dest, node, kind, not opts.get('no_decode'),
525 matchfn, prefix, subrepos=opts.get('subrepos'))
525 matchfn, prefix, subrepos=opts.get('subrepos'))
526
526
527 @command('backout',
527 @command('backout',
528 [('', 'merge', None, _('merge with old dirstate parent after backout')),
528 [('', 'merge', None, _('merge with old dirstate parent after backout')),
529 ('', 'commit', None, _('commit if no conflicts were encountered')),
529 ('', 'commit', None, _('commit if no conflicts were encountered')),
530 ('', 'parent', '',
530 ('', 'parent', '',
531 _('parent to choose when backing out merge (DEPRECATED)'), _('REV')),
531 _('parent to choose when backing out merge (DEPRECATED)'), _('REV')),
532 ('r', 'rev', '', _('revision to backout'), _('REV')),
532 ('r', 'rev', '', _('revision to backout'), _('REV')),
533 ('e', 'edit', False, _('invoke editor on commit messages')),
533 ('e', 'edit', False, _('invoke editor on commit messages')),
534 ] + mergetoolopts + walkopts + commitopts + commitopts2,
534 ] + mergetoolopts + walkopts + commitopts + commitopts2,
535 _('[OPTION]... [-r] REV'))
535 _('[OPTION]... [-r] REV'))
536 def backout(ui, repo, node=None, rev=None, commit=False, **opts):
536 def backout(ui, repo, node=None, rev=None, commit=False, **opts):
537 '''reverse effect of earlier changeset
537 '''reverse effect of earlier changeset
538
538
539 Prepare a new changeset with the effect of REV undone in the
539 Prepare a new changeset with the effect of REV undone in the
540 current working directory.
540 current working directory.
541
541
542 If REV is the parent of the working directory, then this new changeset
542 If REV is the parent of the working directory, then this new changeset
543 is committed automatically. Otherwise, hg needs to merge the
543 is committed automatically. Otherwise, hg needs to merge the
544 changes and the merged result is left uncommitted.
544 changes and the merged result is left uncommitted.
545
545
546 .. note::
546 .. note::
547
547
548 :hg:`backout` cannot be used to fix either an unwanted or
548 :hg:`backout` cannot be used to fix either an unwanted or
549 incorrect merge.
549 incorrect merge.
550
550
551 .. container:: verbose
551 .. container:: verbose
552
552
553 Examples:
553 Examples:
554
554
555 - Reverse the effect of the parent of the working directory.
555 - Reverse the effect of the parent of the working directory.
556 This backout will be committed immediately::
556 This backout will be committed immediately::
557
557
558 hg backout -r .
558 hg backout -r .
559
559
560 - Reverse the effect of previous bad revision 23::
560 - Reverse the effect of previous bad revision 23::
561
561
562 hg backout -r 23
562 hg backout -r 23
563 hg commit -m "Backout revision 23"
563 hg commit -m "Backout revision 23"
564
564
565 - Reverse the effect of previous bad revision 23 and
565 - Reverse the effect of previous bad revision 23 and
566 commit the backout immediately::
566 commit the backout immediately::
567
567
568 hg backout -r 23 --commit
568 hg backout -r 23 --commit
569
569
570 By default, the pending changeset will have one parent,
570 By default, the pending changeset will have one parent,
571 maintaining a linear history. With --merge, the pending
571 maintaining a linear history. With --merge, the pending
572 changeset will instead have two parents: the old parent of the
572 changeset will instead have two parents: the old parent of the
573 working directory and a new child of REV that simply undoes REV.
573 working directory and a new child of REV that simply undoes REV.
574
574
575 Before version 1.7, the behavior without --merge was equivalent
575 Before version 1.7, the behavior without --merge was equivalent
576 to specifying --merge followed by :hg:`update --clean .` to
576 to specifying --merge followed by :hg:`update --clean .` to
577 cancel the merge and leave the child of REV as a head to be
577 cancel the merge and leave the child of REV as a head to be
578 merged separately.
578 merged separately.
579
579
580 See :hg:`help dates` for a list of formats valid for -d/--date.
580 See :hg:`help dates` for a list of formats valid for -d/--date.
581
581
582 See :hg:`help revert` for a way to restore files to the state
582 See :hg:`help revert` for a way to restore files to the state
583 of another revision.
583 of another revision.
584
584
585 Returns 0 on success, 1 if nothing to backout or there are unresolved
585 Returns 0 on success, 1 if nothing to backout or there are unresolved
586 files.
586 files.
587 '''
587 '''
588 wlock = lock = None
588 wlock = lock = None
589 try:
589 try:
590 wlock = repo.wlock()
590 wlock = repo.wlock()
591 lock = repo.lock()
591 lock = repo.lock()
592 return _dobackout(ui, repo, node, rev, commit, **opts)
592 return _dobackout(ui, repo, node, rev, commit, **opts)
593 finally:
593 finally:
594 release(lock, wlock)
594 release(lock, wlock)
595
595
596 def _dobackout(ui, repo, node=None, rev=None, commit=False, **opts):
596 def _dobackout(ui, repo, node=None, rev=None, commit=False, **opts):
597 if rev and node:
597 if rev and node:
598 raise error.Abort(_("please specify just one revision"))
598 raise error.Abort(_("please specify just one revision"))
599
599
600 if not rev:
600 if not rev:
601 rev = node
601 rev = node
602
602
603 if not rev:
603 if not rev:
604 raise error.Abort(_("please specify a revision to backout"))
604 raise error.Abort(_("please specify a revision to backout"))
605
605
606 date = opts.get('date')
606 date = opts.get('date')
607 if date:
607 if date:
608 opts['date'] = util.parsedate(date)
608 opts['date'] = util.parsedate(date)
609
609
610 cmdutil.checkunfinished(repo)
610 cmdutil.checkunfinished(repo)
611 cmdutil.bailifchanged(repo)
611 cmdutil.bailifchanged(repo)
612 node = scmutil.revsingle(repo, rev).node()
612 node = scmutil.revsingle(repo, rev).node()
613
613
614 op1, op2 = repo.dirstate.parents()
614 op1, op2 = repo.dirstate.parents()
615 if not repo.changelog.isancestor(node, op1):
615 if not repo.changelog.isancestor(node, op1):
616 raise error.Abort(_('cannot backout change that is not an ancestor'))
616 raise error.Abort(_('cannot backout change that is not an ancestor'))
617
617
618 p1, p2 = repo.changelog.parents(node)
618 p1, p2 = repo.changelog.parents(node)
619 if p1 == nullid:
619 if p1 == nullid:
620 raise error.Abort(_('cannot backout a change with no parents'))
620 raise error.Abort(_('cannot backout a change with no parents'))
621 if p2 != nullid:
621 if p2 != nullid:
622 if not opts.get('parent'):
622 if not opts.get('parent'):
623 raise error.Abort(_('cannot backout a merge changeset'))
623 raise error.Abort(_('cannot backout a merge changeset'))
624 p = repo.lookup(opts['parent'])
624 p = repo.lookup(opts['parent'])
625 if p not in (p1, p2):
625 if p not in (p1, p2):
626 raise error.Abort(_('%s is not a parent of %s') %
626 raise error.Abort(_('%s is not a parent of %s') %
627 (short(p), short(node)))
627 (short(p), short(node)))
628 parent = p
628 parent = p
629 else:
629 else:
630 if opts.get('parent'):
630 if opts.get('parent'):
631 raise error.Abort(_('cannot use --parent on non-merge changeset'))
631 raise error.Abort(_('cannot use --parent on non-merge changeset'))
632 parent = p1
632 parent = p1
633
633
634 # the backout should appear on the same branch
634 # the backout should appear on the same branch
635 try:
635 try:
636 branch = repo.dirstate.branch()
636 branch = repo.dirstate.branch()
637 bheads = repo.branchheads(branch)
637 bheads = repo.branchheads(branch)
638 rctx = scmutil.revsingle(repo, hex(parent))
638 rctx = scmutil.revsingle(repo, hex(parent))
639 if not opts.get('merge') and op1 != node:
639 if not opts.get('merge') and op1 != node:
640 dsguard = cmdutil.dirstateguard(repo, 'backout')
640 dsguard = cmdutil.dirstateguard(repo, 'backout')
641 try:
641 try:
642 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
642 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
643 'backout')
643 'backout')
644 stats = mergemod.update(repo, parent, True, True, node, False)
644 stats = mergemod.update(repo, parent, True, True, node, False)
645 repo.setparents(op1, op2)
645 repo.setparents(op1, op2)
646 dsguard.close()
646 dsguard.close()
647 hg._showstats(repo, stats)
647 hg._showstats(repo, stats)
648 if stats[3]:
648 if stats[3]:
649 repo.ui.status(_("use 'hg resolve' to retry unresolved "
649 repo.ui.status(_("use 'hg resolve' to retry unresolved "
650 "file merges\n"))
650 "file merges\n"))
651 return 1
651 return 1
652 elif not commit:
652 elif not commit:
653 msg = _("changeset %s backed out, "
653 msg = _("changeset %s backed out, "
654 "don't forget to commit.\n")
654 "don't forget to commit.\n")
655 ui.status(msg % short(node))
655 ui.status(msg % short(node))
656 return 0
656 return 0
657 finally:
657 finally:
658 ui.setconfig('ui', 'forcemerge', '', '')
658 ui.setconfig('ui', 'forcemerge', '', '')
659 lockmod.release(dsguard)
659 lockmod.release(dsguard)
660 else:
660 else:
661 hg.clean(repo, node, show_stats=False)
661 hg.clean(repo, node, show_stats=False)
662 repo.dirstate.setbranch(branch)
662 repo.dirstate.setbranch(branch)
663 cmdutil.revert(ui, repo, rctx, repo.dirstate.parents())
663 cmdutil.revert(ui, repo, rctx, repo.dirstate.parents())
664
664
665
665
666 def commitfunc(ui, repo, message, match, opts):
666 def commitfunc(ui, repo, message, match, opts):
667 editform = 'backout'
667 editform = 'backout'
668 e = cmdutil.getcommiteditor(editform=editform, **opts)
668 e = cmdutil.getcommiteditor(editform=editform, **opts)
669 if not message:
669 if not message:
670 # we don't translate commit messages
670 # we don't translate commit messages
671 message = "Backed out changeset %s" % short(node)
671 message = "Backed out changeset %s" % short(node)
672 e = cmdutil.getcommiteditor(edit=True, editform=editform)
672 e = cmdutil.getcommiteditor(edit=True, editform=editform)
673 return repo.commit(message, opts.get('user'), opts.get('date'),
673 return repo.commit(message, opts.get('user'), opts.get('date'),
674 match, editor=e)
674 match, editor=e)
675 newnode = cmdutil.commit(ui, repo, commitfunc, [], opts)
675 newnode = cmdutil.commit(ui, repo, commitfunc, [], opts)
676 if not newnode:
676 if not newnode:
677 ui.status(_("nothing changed\n"))
677 ui.status(_("nothing changed\n"))
678 return 1
678 return 1
679 cmdutil.commitstatus(repo, newnode, branch, bheads)
679 cmdutil.commitstatus(repo, newnode, branch, bheads)
680
680
681 def nice(node):
681 def nice(node):
682 return '%d:%s' % (repo.changelog.rev(node), short(node))
682 return '%d:%s' % (repo.changelog.rev(node), short(node))
683 ui.status(_('changeset %s backs out changeset %s\n') %
683 ui.status(_('changeset %s backs out changeset %s\n') %
684 (nice(repo.changelog.tip()), nice(node)))
684 (nice(repo.changelog.tip()), nice(node)))
685 if opts.get('merge') and op1 != node:
685 if opts.get('merge') and op1 != node:
686 hg.clean(repo, op1, show_stats=False)
686 hg.clean(repo, op1, show_stats=False)
687 ui.status(_('merging with changeset %s\n')
687 ui.status(_('merging with changeset %s\n')
688 % nice(repo.changelog.tip()))
688 % nice(repo.changelog.tip()))
689 try:
689 try:
690 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
690 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
691 'backout')
691 'backout')
692 return hg.merge(repo, hex(repo.changelog.tip()))
692 return hg.merge(repo, hex(repo.changelog.tip()))
693 finally:
693 finally:
694 ui.setconfig('ui', 'forcemerge', '', '')
694 ui.setconfig('ui', 'forcemerge', '', '')
695 finally:
695 finally:
696 # TODO: get rid of this meaningless try/finally enclosing.
696 # TODO: get rid of this meaningless try/finally enclosing.
697 # this is kept only to reduce changes in a patch.
697 # this is kept only to reduce changes in a patch.
698 pass
698 pass
699 return 0
699 return 0
700
700
701 @command('bisect',
701 @command('bisect',
702 [('r', 'reset', False, _('reset bisect state')),
702 [('r', 'reset', False, _('reset bisect state')),
703 ('g', 'good', False, _('mark changeset good')),
703 ('g', 'good', False, _('mark changeset good')),
704 ('b', 'bad', False, _('mark changeset bad')),
704 ('b', 'bad', False, _('mark changeset bad')),
705 ('s', 'skip', False, _('skip testing changeset')),
705 ('s', 'skip', False, _('skip testing changeset')),
706 ('e', 'extend', False, _('extend the bisect range')),
706 ('e', 'extend', False, _('extend the bisect range')),
707 ('c', 'command', '', _('use command to check changeset state'), _('CMD')),
707 ('c', 'command', '', _('use command to check changeset state'), _('CMD')),
708 ('U', 'noupdate', False, _('do not update to target'))],
708 ('U', 'noupdate', False, _('do not update to target'))],
709 _("[-gbsr] [-U] [-c CMD] [REV]"))
709 _("[-gbsr] [-U] [-c CMD] [REV]"))
710 def bisect(ui, repo, rev=None, extra=None, command=None,
710 def bisect(ui, repo, rev=None, extra=None, command=None,
711 reset=None, good=None, bad=None, skip=None, extend=None,
711 reset=None, good=None, bad=None, skip=None, extend=None,
712 noupdate=None):
712 noupdate=None):
713 """subdivision search of changesets
713 """subdivision search of changesets
714
714
715 This command helps to find changesets which introduce problems. To
715 This command helps to find changesets which introduce problems. To
716 use, mark the earliest changeset you know exhibits the problem as
716 use, mark the earliest changeset you know exhibits the problem as
717 bad, then mark the latest changeset which is free from the problem
717 bad, then mark the latest changeset which is free from the problem
718 as good. Bisect will update your working directory to a revision
718 as good. Bisect will update your working directory to a revision
719 for testing (unless the -U/--noupdate option is specified). Once
719 for testing (unless the -U/--noupdate option is specified). Once
720 you have performed tests, mark the working directory as good or
720 you have performed tests, mark the working directory as good or
721 bad, and bisect will either update to another candidate changeset
721 bad, and bisect will either update to another candidate changeset
722 or announce that it has found the bad revision.
722 or announce that it has found the bad revision.
723
723
724 As a shortcut, you can also use the revision argument to mark a
724 As a shortcut, you can also use the revision argument to mark a
725 revision as good or bad without checking it out first.
725 revision as good or bad without checking it out first.
726
726
727 If you supply a command, it will be used for automatic bisection.
727 If you supply a command, it will be used for automatic bisection.
728 The environment variable HG_NODE will contain the ID of the
728 The environment variable HG_NODE will contain the ID of the
729 changeset being tested. The exit status of the command will be
729 changeset being tested. The exit status of the command will be
730 used to mark revisions as good or bad: status 0 means good, 125
730 used to mark revisions as good or bad: status 0 means good, 125
731 means to skip the revision, 127 (command not found) will abort the
731 means to skip the revision, 127 (command not found) will abort the
732 bisection, and any other non-zero exit status means the revision
732 bisection, and any other non-zero exit status means the revision
733 is bad.
733 is bad.
734
734
735 .. container:: verbose
735 .. container:: verbose
736
736
737 Some examples:
737 Some examples:
738
738
739 - start a bisection with known bad revision 34, and good revision 12::
739 - start a bisection with known bad revision 34, and good revision 12::
740
740
741 hg bisect --bad 34
741 hg bisect --bad 34
742 hg bisect --good 12
742 hg bisect --good 12
743
743
744 - advance the current bisection by marking current revision as good or
744 - advance the current bisection by marking current revision as good or
745 bad::
745 bad::
746
746
747 hg bisect --good
747 hg bisect --good
748 hg bisect --bad
748 hg bisect --bad
749
749
750 - mark the current revision, or a known revision, to be skipped (e.g. if
750 - mark the current revision, or a known revision, to be skipped (e.g. if
751 that revision is not usable because of another issue)::
751 that revision is not usable because of another issue)::
752
752
753 hg bisect --skip
753 hg bisect --skip
754 hg bisect --skip 23
754 hg bisect --skip 23
755
755
756 - skip all revisions that do not touch directories ``foo`` or ``bar``::
756 - skip all revisions that do not touch directories ``foo`` or ``bar``::
757
757
758 hg bisect --skip "!( file('path:foo') & file('path:bar') )"
758 hg bisect --skip "!( file('path:foo') & file('path:bar') )"
759
759
760 - forget the current bisection::
760 - forget the current bisection::
761
761
762 hg bisect --reset
762 hg bisect --reset
763
763
764 - use 'make && make tests' to automatically find the first broken
764 - use 'make && make tests' to automatically find the first broken
765 revision::
765 revision::
766
766
767 hg bisect --reset
767 hg bisect --reset
768 hg bisect --bad 34
768 hg bisect --bad 34
769 hg bisect --good 12
769 hg bisect --good 12
770 hg bisect --command "make && make tests"
770 hg bisect --command "make && make tests"
771
771
772 - see all changesets whose states are already known in the current
772 - see all changesets whose states are already known in the current
773 bisection::
773 bisection::
774
774
775 hg log -r "bisect(pruned)"
775 hg log -r "bisect(pruned)"
776
776
777 - see the changeset currently being bisected (especially useful
777 - see the changeset currently being bisected (especially useful
778 if running with -U/--noupdate)::
778 if running with -U/--noupdate)::
779
779
780 hg log -r "bisect(current)"
780 hg log -r "bisect(current)"
781
781
782 - see all changesets that took part in the current bisection::
782 - see all changesets that took part in the current bisection::
783
783
784 hg log -r "bisect(range)"
784 hg log -r "bisect(range)"
785
785
786 - you can even get a nice graph::
786 - you can even get a nice graph::
787
787
788 hg log --graph -r "bisect(range)"
788 hg log --graph -r "bisect(range)"
789
789
790 See :hg:`help revsets` for more about the `bisect()` keyword.
790 See :hg:`help revsets` for more about the `bisect()` keyword.
791
791
792 Returns 0 on success.
792 Returns 0 on success.
793 """
793 """
794 def extendbisectrange(nodes, good):
794 def extendbisectrange(nodes, good):
795 # bisect is incomplete when it ends on a merge node and
795 # bisect is incomplete when it ends on a merge node and
796 # one of the parent was not checked.
796 # one of the parent was not checked.
797 parents = repo[nodes[0]].parents()
797 parents = repo[nodes[0]].parents()
798 if len(parents) > 1:
798 if len(parents) > 1:
799 if good:
799 if good:
800 side = state['bad']
800 side = state['bad']
801 else:
801 else:
802 side = state['good']
802 side = state['good']
803 num = len(set(i.node() for i in parents) & set(side))
803 num = len(set(i.node() for i in parents) & set(side))
804 if num == 1:
804 if num == 1:
805 return parents[0].ancestor(parents[1])
805 return parents[0].ancestor(parents[1])
806 return None
806 return None
807
807
808 def print_result(nodes, good):
808 def print_result(nodes, good):
809 displayer = cmdutil.show_changeset(ui, repo, {})
809 displayer = cmdutil.show_changeset(ui, repo, {})
810 if len(nodes) == 1:
810 if len(nodes) == 1:
811 # narrowed it down to a single revision
811 # narrowed it down to a single revision
812 if good:
812 if good:
813 ui.write(_("The first good revision is:\n"))
813 ui.write(_("The first good revision is:\n"))
814 else:
814 else:
815 ui.write(_("The first bad revision is:\n"))
815 ui.write(_("The first bad revision is:\n"))
816 displayer.show(repo[nodes[0]])
816 displayer.show(repo[nodes[0]])
817 extendnode = extendbisectrange(nodes, good)
817 extendnode = extendbisectrange(nodes, good)
818 if extendnode is not None:
818 if extendnode is not None:
819 ui.write(_('Not all ancestors of this changeset have been'
819 ui.write(_('Not all ancestors of this changeset have been'
820 ' checked.\nUse bisect --extend to continue the '
820 ' checked.\nUse bisect --extend to continue the '
821 'bisection from\nthe common ancestor, %s.\n')
821 'bisection from\nthe common ancestor, %s.\n')
822 % extendnode)
822 % extendnode)
823 else:
823 else:
824 # multiple possible revisions
824 # multiple possible revisions
825 if good:
825 if good:
826 ui.write(_("Due to skipped revisions, the first "
826 ui.write(_("Due to skipped revisions, the first "
827 "good revision could be any of:\n"))
827 "good revision could be any of:\n"))
828 else:
828 else:
829 ui.write(_("Due to skipped revisions, the first "
829 ui.write(_("Due to skipped revisions, the first "
830 "bad revision could be any of:\n"))
830 "bad revision could be any of:\n"))
831 for n in nodes:
831 for n in nodes:
832 displayer.show(repo[n])
832 displayer.show(repo[n])
833 displayer.close()
833 displayer.close()
834
834
835 def check_state(state, interactive=True):
835 def check_state(state, interactive=True):
836 if not state['good'] or not state['bad']:
836 if not state['good'] or not state['bad']:
837 if (good or bad or skip or reset) and interactive:
837 if (good or bad or skip or reset) and interactive:
838 return
838 return
839 if not state['good']:
839 if not state['good']:
840 raise error.Abort(_('cannot bisect (no known good revisions)'))
840 raise error.Abort(_('cannot bisect (no known good revisions)'))
841 else:
841 else:
842 raise error.Abort(_('cannot bisect (no known bad revisions)'))
842 raise error.Abort(_('cannot bisect (no known bad revisions)'))
843 return True
843 return True
844
844
845 # backward compatibility
845 # backward compatibility
846 if rev in "good bad reset init".split():
846 if rev in "good bad reset init".split():
847 ui.warn(_("(use of 'hg bisect <cmd>' is deprecated)\n"))
847 ui.warn(_("(use of 'hg bisect <cmd>' is deprecated)\n"))
848 cmd, rev, extra = rev, extra, None
848 cmd, rev, extra = rev, extra, None
849 if cmd == "good":
849 if cmd == "good":
850 good = True
850 good = True
851 elif cmd == "bad":
851 elif cmd == "bad":
852 bad = True
852 bad = True
853 else:
853 else:
854 reset = True
854 reset = True
855 elif extra or good + bad + skip + reset + extend + bool(command) > 1:
855 elif extra or good + bad + skip + reset + extend + bool(command) > 1:
856 raise error.Abort(_('incompatible arguments'))
856 raise error.Abort(_('incompatible arguments'))
857
857
858 cmdutil.checkunfinished(repo)
858 cmdutil.checkunfinished(repo)
859
859
860 if reset:
860 if reset:
861 p = repo.join("bisect.state")
861 p = repo.join("bisect.state")
862 if os.path.exists(p):
862 if os.path.exists(p):
863 os.unlink(p)
863 os.unlink(p)
864 return
864 return
865
865
866 state = hbisect.load_state(repo)
866 state = hbisect.load_state(repo)
867
867
868 if command:
868 if command:
869 changesets = 1
869 changesets = 1
870 if noupdate:
870 if noupdate:
871 try:
871 try:
872 node = state['current'][0]
872 node = state['current'][0]
873 except LookupError:
873 except LookupError:
874 raise error.Abort(_('current bisect revision is unknown - '
874 raise error.Abort(_('current bisect revision is unknown - '
875 'start a new bisect to fix'))
875 'start a new bisect to fix'))
876 else:
876 else:
877 node, p2 = repo.dirstate.parents()
877 node, p2 = repo.dirstate.parents()
878 if p2 != nullid:
878 if p2 != nullid:
879 raise error.Abort(_('current bisect revision is a merge'))
879 raise error.Abort(_('current bisect revision is a merge'))
880 try:
880 try:
881 while changesets:
881 while changesets:
882 # update state
882 # update state
883 state['current'] = [node]
883 state['current'] = [node]
884 hbisect.save_state(repo, state)
884 hbisect.save_state(repo, state)
885 status = ui.system(command, environ={'HG_NODE': hex(node)})
885 status = ui.system(command, environ={'HG_NODE': hex(node)})
886 if status == 125:
886 if status == 125:
887 transition = "skip"
887 transition = "skip"
888 elif status == 0:
888 elif status == 0:
889 transition = "good"
889 transition = "good"
890 # status < 0 means process was killed
890 # status < 0 means process was killed
891 elif status == 127:
891 elif status == 127:
892 raise error.Abort(_("failed to execute %s") % command)
892 raise error.Abort(_("failed to execute %s") % command)
893 elif status < 0:
893 elif status < 0:
894 raise error.Abort(_("%s killed") % command)
894 raise error.Abort(_("%s killed") % command)
895 else:
895 else:
896 transition = "bad"
896 transition = "bad"
897 ctx = scmutil.revsingle(repo, rev, node)
897 ctx = scmutil.revsingle(repo, rev, node)
898 rev = None # clear for future iterations
898 rev = None # clear for future iterations
899 state[transition].append(ctx.node())
899 state[transition].append(ctx.node())
900 ui.status(_('changeset %d:%s: %s\n') % (ctx, ctx, transition))
900 ui.status(_('changeset %d:%s: %s\n') % (ctx, ctx, transition))
901 check_state(state, interactive=False)
901 check_state(state, interactive=False)
902 # bisect
902 # bisect
903 nodes, changesets, bgood = hbisect.bisect(repo.changelog, state)
903 nodes, changesets, bgood = hbisect.bisect(repo.changelog, state)
904 # update to next check
904 # update to next check
905 node = nodes[0]
905 node = nodes[0]
906 if not noupdate:
906 if not noupdate:
907 cmdutil.bailifchanged(repo)
907 cmdutil.bailifchanged(repo)
908 hg.clean(repo, node, show_stats=False)
908 hg.clean(repo, node, show_stats=False)
909 finally:
909 finally:
910 state['current'] = [node]
910 state['current'] = [node]
911 hbisect.save_state(repo, state)
911 hbisect.save_state(repo, state)
912 print_result(nodes, bgood)
912 print_result(nodes, bgood)
913 return
913 return
914
914
915 # update state
915 # update state
916
916
917 if rev:
917 if rev:
918 nodes = [repo.lookup(i) for i in scmutil.revrange(repo, [rev])]
918 nodes = [repo.lookup(i) for i in scmutil.revrange(repo, [rev])]
919 else:
919 else:
920 nodes = [repo.lookup('.')]
920 nodes = [repo.lookup('.')]
921
921
922 if good or bad or skip:
922 if good or bad or skip:
923 if good:
923 if good:
924 state['good'] += nodes
924 state['good'] += nodes
925 elif bad:
925 elif bad:
926 state['bad'] += nodes
926 state['bad'] += nodes
927 elif skip:
927 elif skip:
928 state['skip'] += nodes
928 state['skip'] += nodes
929 hbisect.save_state(repo, state)
929 hbisect.save_state(repo, state)
930
930
931 if not check_state(state):
931 if not check_state(state):
932 return
932 return
933
933
934 # actually bisect
934 # actually bisect
935 nodes, changesets, good = hbisect.bisect(repo.changelog, state)
935 nodes, changesets, good = hbisect.bisect(repo.changelog, state)
936 if extend:
936 if extend:
937 if not changesets:
937 if not changesets:
938 extendnode = extendbisectrange(nodes, good)
938 extendnode = extendbisectrange(nodes, good)
939 if extendnode is not None:
939 if extendnode is not None:
940 ui.write(_("Extending search to changeset %d:%s\n")
940 ui.write(_("Extending search to changeset %d:%s\n")
941 % (extendnode.rev(), extendnode))
941 % (extendnode.rev(), extendnode))
942 state['current'] = [extendnode.node()]
942 state['current'] = [extendnode.node()]
943 hbisect.save_state(repo, state)
943 hbisect.save_state(repo, state)
944 if noupdate:
944 if noupdate:
945 return
945 return
946 cmdutil.bailifchanged(repo)
946 cmdutil.bailifchanged(repo)
947 return hg.clean(repo, extendnode.node())
947 return hg.clean(repo, extendnode.node())
948 raise error.Abort(_("nothing to extend"))
948 raise error.Abort(_("nothing to extend"))
949
949
950 if changesets == 0:
950 if changesets == 0:
951 print_result(nodes, good)
951 print_result(nodes, good)
952 else:
952 else:
953 assert len(nodes) == 1 # only a single node can be tested next
953 assert len(nodes) == 1 # only a single node can be tested next
954 node = nodes[0]
954 node = nodes[0]
955 # compute the approximate number of remaining tests
955 # compute the approximate number of remaining tests
956 tests, size = 0, 2
956 tests, size = 0, 2
957 while size <= changesets:
957 while size <= changesets:
958 tests, size = tests + 1, size * 2
958 tests, size = tests + 1, size * 2
959 rev = repo.changelog.rev(node)
959 rev = repo.changelog.rev(node)
960 ui.write(_("Testing changeset %d:%s "
960 ui.write(_("Testing changeset %d:%s "
961 "(%d changesets remaining, ~%d tests)\n")
961 "(%d changesets remaining, ~%d tests)\n")
962 % (rev, short(node), changesets, tests))
962 % (rev, short(node), changesets, tests))
963 state['current'] = [node]
963 state['current'] = [node]
964 hbisect.save_state(repo, state)
964 hbisect.save_state(repo, state)
965 if not noupdate:
965 if not noupdate:
966 cmdutil.bailifchanged(repo)
966 cmdutil.bailifchanged(repo)
967 return hg.clean(repo, node)
967 return hg.clean(repo, node)
968
968
969 @command('bookmarks|bookmark',
969 @command('bookmarks|bookmark',
970 [('f', 'force', False, _('force')),
970 [('f', 'force', False, _('force')),
971 ('r', 'rev', '', _('revision'), _('REV')),
971 ('r', 'rev', '', _('revision'), _('REV')),
972 ('d', 'delete', False, _('delete a given bookmark')),
972 ('d', 'delete', False, _('delete a given bookmark')),
973 ('m', 'rename', '', _('rename a given bookmark'), _('OLD')),
973 ('m', 'rename', '', _('rename a given bookmark'), _('OLD')),
974 ('i', 'inactive', False, _('mark a bookmark inactive')),
974 ('i', 'inactive', False, _('mark a bookmark inactive')),
975 ] + formatteropts,
975 ] + formatteropts,
976 _('hg bookmarks [OPTIONS]... [NAME]...'))
976 _('hg bookmarks [OPTIONS]... [NAME]...'))
977 def bookmark(ui, repo, *names, **opts):
977 def bookmark(ui, repo, *names, **opts):
978 '''create a new bookmark or list existing bookmarks
978 '''create a new bookmark or list existing bookmarks
979
979
980 Bookmarks are labels on changesets to help track lines of development.
980 Bookmarks are labels on changesets to help track lines of development.
981 Bookmarks are unversioned and can be moved, renamed and deleted.
981 Bookmarks are unversioned and can be moved, renamed and deleted.
982 Deleting or moving a bookmark has no effect on the associated changesets.
982 Deleting or moving a bookmark has no effect on the associated changesets.
983
983
984 Creating or updating to a bookmark causes it to be marked as 'active'.
984 Creating or updating to a bookmark causes it to be marked as 'active'.
985 The active bookmark is indicated with a '*'.
985 The active bookmark is indicated with a '*'.
986 When a commit is made, the active bookmark will advance to the new commit.
986 When a commit is made, the active bookmark will advance to the new commit.
987 A plain :hg:`update` will also advance an active bookmark, if possible.
987 A plain :hg:`update` will also advance an active bookmark, if possible.
988 Updating away from a bookmark will cause it to be deactivated.
988 Updating away from a bookmark will cause it to be deactivated.
989
989
990 Bookmarks can be pushed and pulled between repositories (see
990 Bookmarks can be pushed and pulled between repositories (see
991 :hg:`help push` and :hg:`help pull`). If a shared bookmark has
991 :hg:`help push` and :hg:`help pull`). If a shared bookmark has
992 diverged, a new 'divergent bookmark' of the form 'name@path' will
992 diverged, a new 'divergent bookmark' of the form 'name@path' will
993 be created. Using :hg:`merge` will resolve the divergence.
993 be created. Using :hg:`merge` will resolve the divergence.
994
994
995 A bookmark named '@' has the special property that :hg:`clone` will
995 A bookmark named '@' has the special property that :hg:`clone` will
996 check it out by default if it exists.
996 check it out by default if it exists.
997
997
998 .. container:: verbose
998 .. container:: verbose
999
999
1000 Examples:
1000 Examples:
1001
1001
1002 - create an active bookmark for a new line of development::
1002 - create an active bookmark for a new line of development::
1003
1003
1004 hg book new-feature
1004 hg book new-feature
1005
1005
1006 - create an inactive bookmark as a place marker::
1006 - create an inactive bookmark as a place marker::
1007
1007
1008 hg book -i reviewed
1008 hg book -i reviewed
1009
1009
1010 - create an inactive bookmark on another changeset::
1010 - create an inactive bookmark on another changeset::
1011
1011
1012 hg book -r .^ tested
1012 hg book -r .^ tested
1013
1013
1014 - rename bookmark turkey to dinner::
1014 - rename bookmark turkey to dinner::
1015
1015
1016 hg book -m turkey dinner
1016 hg book -m turkey dinner
1017
1017
1018 - move the '@' bookmark from another branch::
1018 - move the '@' bookmark from another branch::
1019
1019
1020 hg book -f @
1020 hg book -f @
1021 '''
1021 '''
1022 force = opts.get('force')
1022 force = opts.get('force')
1023 rev = opts.get('rev')
1023 rev = opts.get('rev')
1024 delete = opts.get('delete')
1024 delete = opts.get('delete')
1025 rename = opts.get('rename')
1025 rename = opts.get('rename')
1026 inactive = opts.get('inactive')
1026 inactive = opts.get('inactive')
1027
1027
1028 def checkformat(mark):
1028 def checkformat(mark):
1029 mark = mark.strip()
1029 mark = mark.strip()
1030 if not mark:
1030 if not mark:
1031 raise error.Abort(_("bookmark names cannot consist entirely of "
1031 raise error.Abort(_("bookmark names cannot consist entirely of "
1032 "whitespace"))
1032 "whitespace"))
1033 scmutil.checknewlabel(repo, mark, 'bookmark')
1033 scmutil.checknewlabel(repo, mark, 'bookmark')
1034 return mark
1034 return mark
1035
1035
1036 def checkconflict(repo, mark, cur, force=False, target=None):
1036 def checkconflict(repo, mark, cur, force=False, target=None):
1037 if mark in marks and not force:
1037 if mark in marks and not force:
1038 if target:
1038 if target:
1039 if marks[mark] == target and target == cur:
1039 if marks[mark] == target and target == cur:
1040 # re-activating a bookmark
1040 # re-activating a bookmark
1041 return
1041 return
1042 anc = repo.changelog.ancestors([repo[target].rev()])
1042 anc = repo.changelog.ancestors([repo[target].rev()])
1043 bmctx = repo[marks[mark]]
1043 bmctx = repo[marks[mark]]
1044 divs = [repo[b].node() for b in marks
1044 divs = [repo[b].node() for b in marks
1045 if b.split('@', 1)[0] == mark.split('@', 1)[0]]
1045 if b.split('@', 1)[0] == mark.split('@', 1)[0]]
1046
1046
1047 # allow resolving a single divergent bookmark even if moving
1047 # allow resolving a single divergent bookmark even if moving
1048 # the bookmark across branches when a revision is specified
1048 # the bookmark across branches when a revision is specified
1049 # that contains a divergent bookmark
1049 # that contains a divergent bookmark
1050 if bmctx.rev() not in anc and target in divs:
1050 if bmctx.rev() not in anc and target in divs:
1051 bookmarks.deletedivergent(repo, [target], mark)
1051 bookmarks.deletedivergent(repo, [target], mark)
1052 return
1052 return
1053
1053
1054 deletefrom = [b for b in divs
1054 deletefrom = [b for b in divs
1055 if repo[b].rev() in anc or b == target]
1055 if repo[b].rev() in anc or b == target]
1056 bookmarks.deletedivergent(repo, deletefrom, mark)
1056 bookmarks.deletedivergent(repo, deletefrom, mark)
1057 if bookmarks.validdest(repo, bmctx, repo[target]):
1057 if bookmarks.validdest(repo, bmctx, repo[target]):
1058 ui.status(_("moving bookmark '%s' forward from %s\n") %
1058 ui.status(_("moving bookmark '%s' forward from %s\n") %
1059 (mark, short(bmctx.node())))
1059 (mark, short(bmctx.node())))
1060 return
1060 return
1061 raise error.Abort(_("bookmark '%s' already exists "
1061 raise error.Abort(_("bookmark '%s' already exists "
1062 "(use -f to force)") % mark)
1062 "(use -f to force)") % mark)
1063 if ((mark in repo.branchmap() or mark == repo.dirstate.branch())
1063 if ((mark in repo.branchmap() or mark == repo.dirstate.branch())
1064 and not force):
1064 and not force):
1065 raise error.Abort(
1065 raise error.Abort(
1066 _("a bookmark cannot have the name of an existing branch"))
1066 _("a bookmark cannot have the name of an existing branch"))
1067
1067
1068 if delete and rename:
1068 if delete and rename:
1069 raise error.Abort(_("--delete and --rename are incompatible"))
1069 raise error.Abort(_("--delete and --rename are incompatible"))
1070 if delete and rev:
1070 if delete and rev:
1071 raise error.Abort(_("--rev is incompatible with --delete"))
1071 raise error.Abort(_("--rev is incompatible with --delete"))
1072 if rename and rev:
1072 if rename and rev:
1073 raise error.Abort(_("--rev is incompatible with --rename"))
1073 raise error.Abort(_("--rev is incompatible with --rename"))
1074 if not names and (delete or rev):
1074 if not names and (delete or rev):
1075 raise error.Abort(_("bookmark name required"))
1075 raise error.Abort(_("bookmark name required"))
1076
1076
1077 if delete or rename or names or inactive:
1077 if delete or rename or names or inactive:
1078 wlock = lock = tr = None
1078 wlock = lock = tr = None
1079 try:
1079 try:
1080 wlock = repo.wlock()
1080 wlock = repo.wlock()
1081 lock = repo.lock()
1081 lock = repo.lock()
1082 cur = repo.changectx('.').node()
1082 cur = repo.changectx('.').node()
1083 marks = repo._bookmarks
1083 marks = repo._bookmarks
1084 if delete:
1084 if delete:
1085 tr = repo.transaction('bookmark')
1085 tr = repo.transaction('bookmark')
1086 for mark in names:
1086 for mark in names:
1087 if mark not in marks:
1087 if mark not in marks:
1088 raise error.Abort(_("bookmark '%s' does not exist") %
1088 raise error.Abort(_("bookmark '%s' does not exist") %
1089 mark)
1089 mark)
1090 if mark == repo._activebookmark:
1090 if mark == repo._activebookmark:
1091 bookmarks.deactivate(repo)
1091 bookmarks.deactivate(repo)
1092 del marks[mark]
1092 del marks[mark]
1093
1093
1094 elif rename:
1094 elif rename:
1095 tr = repo.transaction('bookmark')
1095 tr = repo.transaction('bookmark')
1096 if not names:
1096 if not names:
1097 raise error.Abort(_("new bookmark name required"))
1097 raise error.Abort(_("new bookmark name required"))
1098 elif len(names) > 1:
1098 elif len(names) > 1:
1099 raise error.Abort(_("only one new bookmark name allowed"))
1099 raise error.Abort(_("only one new bookmark name allowed"))
1100 mark = checkformat(names[0])
1100 mark = checkformat(names[0])
1101 if rename not in marks:
1101 if rename not in marks:
1102 raise error.Abort(_("bookmark '%s' does not exist")
1102 raise error.Abort(_("bookmark '%s' does not exist")
1103 % rename)
1103 % rename)
1104 checkconflict(repo, mark, cur, force)
1104 checkconflict(repo, mark, cur, force)
1105 marks[mark] = marks[rename]
1105 marks[mark] = marks[rename]
1106 if repo._activebookmark == rename and not inactive:
1106 if repo._activebookmark == rename and not inactive:
1107 bookmarks.activate(repo, mark)
1107 bookmarks.activate(repo, mark)
1108 del marks[rename]
1108 del marks[rename]
1109 elif names:
1109 elif names:
1110 tr = repo.transaction('bookmark')
1110 tr = repo.transaction('bookmark')
1111 newact = None
1111 newact = None
1112 for mark in names:
1112 for mark in names:
1113 mark = checkformat(mark)
1113 mark = checkformat(mark)
1114 if newact is None:
1114 if newact is None:
1115 newact = mark
1115 newact = mark
1116 if inactive and mark == repo._activebookmark:
1116 if inactive and mark == repo._activebookmark:
1117 bookmarks.deactivate(repo)
1117 bookmarks.deactivate(repo)
1118 return
1118 return
1119 tgt = cur
1119 tgt = cur
1120 if rev:
1120 if rev:
1121 tgt = scmutil.revsingle(repo, rev).node()
1121 tgt = scmutil.revsingle(repo, rev).node()
1122 checkconflict(repo, mark, cur, force, tgt)
1122 checkconflict(repo, mark, cur, force, tgt)
1123 marks[mark] = tgt
1123 marks[mark] = tgt
1124 if not inactive and cur == marks[newact] and not rev:
1124 if not inactive and cur == marks[newact] and not rev:
1125 bookmarks.activate(repo, newact)
1125 bookmarks.activate(repo, newact)
1126 elif cur != tgt and newact == repo._activebookmark:
1126 elif cur != tgt and newact == repo._activebookmark:
1127 bookmarks.deactivate(repo)
1127 bookmarks.deactivate(repo)
1128 elif inactive:
1128 elif inactive:
1129 if len(marks) == 0:
1129 if len(marks) == 0:
1130 ui.status(_("no bookmarks set\n"))
1130 ui.status(_("no bookmarks set\n"))
1131 elif not repo._activebookmark:
1131 elif not repo._activebookmark:
1132 ui.status(_("no active bookmark\n"))
1132 ui.status(_("no active bookmark\n"))
1133 else:
1133 else:
1134 bookmarks.deactivate(repo)
1134 bookmarks.deactivate(repo)
1135 if tr is not None:
1135 if tr is not None:
1136 marks.recordchange(tr)
1136 marks.recordchange(tr)
1137 tr.close()
1137 tr.close()
1138 finally:
1138 finally:
1139 lockmod.release(tr, lock, wlock)
1139 lockmod.release(tr, lock, wlock)
1140 else: # show bookmarks
1140 else: # show bookmarks
1141 fm = ui.formatter('bookmarks', opts)
1141 fm = ui.formatter('bookmarks', opts)
1142 hexfn = fm.hexfunc
1142 hexfn = fm.hexfunc
1143 marks = repo._bookmarks
1143 marks = repo._bookmarks
1144 if len(marks) == 0 and not fm:
1144 if len(marks) == 0 and not fm:
1145 ui.status(_("no bookmarks set\n"))
1145 ui.status(_("no bookmarks set\n"))
1146 for bmark, n in sorted(marks.iteritems()):
1146 for bmark, n in sorted(marks.iteritems()):
1147 active = repo._activebookmark
1147 active = repo._activebookmark
1148 if bmark == active:
1148 if bmark == active:
1149 prefix, label = '*', activebookmarklabel
1149 prefix, label = '*', activebookmarklabel
1150 else:
1150 else:
1151 prefix, label = ' ', ''
1151 prefix, label = ' ', ''
1152
1152
1153 fm.startitem()
1153 fm.startitem()
1154 if not ui.quiet:
1154 if not ui.quiet:
1155 fm.plain(' %s ' % prefix, label=label)
1155 fm.plain(' %s ' % prefix, label=label)
1156 fm.write('bookmark', '%s', bmark, label=label)
1156 fm.write('bookmark', '%s', bmark, label=label)
1157 pad = " " * (25 - encoding.colwidth(bmark))
1157 pad = " " * (25 - encoding.colwidth(bmark))
1158 fm.condwrite(not ui.quiet, 'rev node', pad + ' %d:%s',
1158 fm.condwrite(not ui.quiet, 'rev node', pad + ' %d:%s',
1159 repo.changelog.rev(n), hexfn(n), label=label)
1159 repo.changelog.rev(n), hexfn(n), label=label)
1160 fm.data(active=(bmark == active))
1160 fm.data(active=(bmark == active))
1161 fm.plain('\n')
1161 fm.plain('\n')
1162 fm.end()
1162 fm.end()
1163
1163
1164 @command('branch',
1164 @command('branch',
1165 [('f', 'force', None,
1165 [('f', 'force', None,
1166 _('set branch name even if it shadows an existing branch')),
1166 _('set branch name even if it shadows an existing branch')),
1167 ('C', 'clean', None, _('reset branch name to parent branch name'))],
1167 ('C', 'clean', None, _('reset branch name to parent branch name'))],
1168 _('[-fC] [NAME]'))
1168 _('[-fC] [NAME]'))
1169 def branch(ui, repo, label=None, **opts):
1169 def branch(ui, repo, label=None, **opts):
1170 """set or show the current branch name
1170 """set or show the current branch name
1171
1171
1172 .. note::
1172 .. note::
1173
1173
1174 Branch names are permanent and global. Use :hg:`bookmark` to create a
1174 Branch names are permanent and global. Use :hg:`bookmark` to create a
1175 light-weight bookmark instead. See :hg:`help glossary` for more
1175 light-weight bookmark instead. See :hg:`help glossary` for more
1176 information about named branches and bookmarks.
1176 information about named branches and bookmarks.
1177
1177
1178 With no argument, show the current branch name. With one argument,
1178 With no argument, show the current branch name. With one argument,
1179 set the working directory branch name (the branch will not exist
1179 set the working directory branch name (the branch will not exist
1180 in the repository until the next commit). Standard practice
1180 in the repository until the next commit). Standard practice
1181 recommends that primary development take place on the 'default'
1181 recommends that primary development take place on the 'default'
1182 branch.
1182 branch.
1183
1183
1184 Unless -f/--force is specified, branch will not let you set a
1184 Unless -f/--force is specified, branch will not let you set a
1185 branch name that already exists.
1185 branch name that already exists.
1186
1186
1187 Use -C/--clean to reset the working directory branch to that of
1187 Use -C/--clean to reset the working directory branch to that of
1188 the parent of the working directory, negating a previous branch
1188 the parent of the working directory, negating a previous branch
1189 change.
1189 change.
1190
1190
1191 Use the command :hg:`update` to switch to an existing branch. Use
1191 Use the command :hg:`update` to switch to an existing branch. Use
1192 :hg:`commit --close-branch` to mark this branch head as closed.
1192 :hg:`commit --close-branch` to mark this branch head as closed.
1193 When all heads of a branch are closed, the branch will be
1193 When all heads of a branch are closed, the branch will be
1194 considered closed.
1194 considered closed.
1195
1195
1196 Returns 0 on success.
1196 Returns 0 on success.
1197 """
1197 """
1198 if label:
1198 if label:
1199 label = label.strip()
1199 label = label.strip()
1200
1200
1201 if not opts.get('clean') and not label:
1201 if not opts.get('clean') and not label:
1202 ui.write("%s\n" % repo.dirstate.branch())
1202 ui.write("%s\n" % repo.dirstate.branch())
1203 return
1203 return
1204
1204
1205 wlock = repo.wlock()
1205 wlock = repo.wlock()
1206 try:
1206 try:
1207 if opts.get('clean'):
1207 if opts.get('clean'):
1208 label = repo[None].p1().branch()
1208 label = repo[None].p1().branch()
1209 repo.dirstate.setbranch(label)
1209 repo.dirstate.setbranch(label)
1210 ui.status(_('reset working directory to branch %s\n') % label)
1210 ui.status(_('reset working directory to branch %s\n') % label)
1211 elif label:
1211 elif label:
1212 if not opts.get('force') and label in repo.branchmap():
1212 if not opts.get('force') and label in repo.branchmap():
1213 if label not in [p.branch() for p in repo[None].parents()]:
1213 if label not in [p.branch() for p in repo[None].parents()]:
1214 raise error.Abort(_('a branch of the same name already'
1214 raise error.Abort(_('a branch of the same name already'
1215 ' exists'),
1215 ' exists'),
1216 # i18n: "it" refers to an existing branch
1216 # i18n: "it" refers to an existing branch
1217 hint=_("use 'hg update' to switch to it"))
1217 hint=_("use 'hg update' to switch to it"))
1218 scmutil.checknewlabel(repo, label, 'branch')
1218 scmutil.checknewlabel(repo, label, 'branch')
1219 repo.dirstate.setbranch(label)
1219 repo.dirstate.setbranch(label)
1220 ui.status(_('marked working directory as branch %s\n') % label)
1220 ui.status(_('marked working directory as branch %s\n') % label)
1221
1221
1222 # find any open named branches aside from default
1222 # find any open named branches aside from default
1223 others = [n for n, h, t, c in repo.branchmap().iterbranches()
1223 others = [n for n, h, t, c in repo.branchmap().iterbranches()
1224 if n != "default" and not c]
1224 if n != "default" and not c]
1225 if not others:
1225 if not others:
1226 ui.status(_('(branches are permanent and global, '
1226 ui.status(_('(branches are permanent and global, '
1227 'did you want a bookmark?)\n'))
1227 'did you want a bookmark?)\n'))
1228 finally:
1228 finally:
1229 wlock.release()
1229 wlock.release()
1230
1230
1231 @command('branches',
1231 @command('branches',
1232 [('a', 'active', False,
1232 [('a', 'active', False,
1233 _('show only branches that have unmerged heads (DEPRECATED)')),
1233 _('show only branches that have unmerged heads (DEPRECATED)')),
1234 ('c', 'closed', False, _('show normal and closed branches')),
1234 ('c', 'closed', False, _('show normal and closed branches')),
1235 ] + formatteropts,
1235 ] + formatteropts,
1236 _('[-ac]'))
1236 _('[-ac]'))
1237 def branches(ui, repo, active=False, closed=False, **opts):
1237 def branches(ui, repo, active=False, closed=False, **opts):
1238 """list repository named branches
1238 """list repository named branches
1239
1239
1240 List the repository's named branches, indicating which ones are
1240 List the repository's named branches, indicating which ones are
1241 inactive. If -c/--closed is specified, also list branches which have
1241 inactive. If -c/--closed is specified, also list branches which have
1242 been marked closed (see :hg:`commit --close-branch`).
1242 been marked closed (see :hg:`commit --close-branch`).
1243
1243
1244 Use the command :hg:`update` to switch to an existing branch.
1244 Use the command :hg:`update` to switch to an existing branch.
1245
1245
1246 Returns 0.
1246 Returns 0.
1247 """
1247 """
1248
1248
1249 fm = ui.formatter('branches', opts)
1249 fm = ui.formatter('branches', opts)
1250 hexfunc = fm.hexfunc
1250 hexfunc = fm.hexfunc
1251
1251
1252 allheads = set(repo.heads())
1252 allheads = set(repo.heads())
1253 branches = []
1253 branches = []
1254 for tag, heads, tip, isclosed in repo.branchmap().iterbranches():
1254 for tag, heads, tip, isclosed in repo.branchmap().iterbranches():
1255 isactive = not isclosed and bool(set(heads) & allheads)
1255 isactive = not isclosed and bool(set(heads) & allheads)
1256 branches.append((tag, repo[tip], isactive, not isclosed))
1256 branches.append((tag, repo[tip], isactive, not isclosed))
1257 branches.sort(key=lambda i: (i[2], i[1].rev(), i[0], i[3]),
1257 branches.sort(key=lambda i: (i[2], i[1].rev(), i[0], i[3]),
1258 reverse=True)
1258 reverse=True)
1259
1259
1260 for tag, ctx, isactive, isopen in branches:
1260 for tag, ctx, isactive, isopen in branches:
1261 if active and not isactive:
1261 if active and not isactive:
1262 continue
1262 continue
1263 if isactive:
1263 if isactive:
1264 label = 'branches.active'
1264 label = 'branches.active'
1265 notice = ''
1265 notice = ''
1266 elif not isopen:
1266 elif not isopen:
1267 if not closed:
1267 if not closed:
1268 continue
1268 continue
1269 label = 'branches.closed'
1269 label = 'branches.closed'
1270 notice = _(' (closed)')
1270 notice = _(' (closed)')
1271 else:
1271 else:
1272 label = 'branches.inactive'
1272 label = 'branches.inactive'
1273 notice = _(' (inactive)')
1273 notice = _(' (inactive)')
1274 current = (tag == repo.dirstate.branch())
1274 current = (tag == repo.dirstate.branch())
1275 if current:
1275 if current:
1276 label = 'branches.current'
1276 label = 'branches.current'
1277
1277
1278 fm.startitem()
1278 fm.startitem()
1279 fm.write('branch', '%s', tag, label=label)
1279 fm.write('branch', '%s', tag, label=label)
1280 rev = ctx.rev()
1280 rev = ctx.rev()
1281 padsize = max(31 - len(str(rev)) - encoding.colwidth(tag), 0)
1281 padsize = max(31 - len(str(rev)) - encoding.colwidth(tag), 0)
1282 fmt = ' ' * padsize + ' %d:%s'
1282 fmt = ' ' * padsize + ' %d:%s'
1283 fm.condwrite(not ui.quiet, 'rev node', fmt, rev, hexfunc(ctx.node()),
1283 fm.condwrite(not ui.quiet, 'rev node', fmt, rev, hexfunc(ctx.node()),
1284 label='log.changeset changeset.%s' % ctx.phasestr())
1284 label='log.changeset changeset.%s' % ctx.phasestr())
1285 fm.data(active=isactive, closed=not isopen, current=current)
1285 fm.data(active=isactive, closed=not isopen, current=current)
1286 if not ui.quiet:
1286 if not ui.quiet:
1287 fm.plain(notice)
1287 fm.plain(notice)
1288 fm.plain('\n')
1288 fm.plain('\n')
1289 fm.end()
1289 fm.end()
1290
1290
1291 @command('bundle',
1291 @command('bundle',
1292 [('f', 'force', None, _('run even when the destination is unrelated')),
1292 [('f', 'force', None, _('run even when the destination is unrelated')),
1293 ('r', 'rev', [], _('a changeset intended to be added to the destination'),
1293 ('r', 'rev', [], _('a changeset intended to be added to the destination'),
1294 _('REV')),
1294 _('REV')),
1295 ('b', 'branch', [], _('a specific branch you would like to bundle'),
1295 ('b', 'branch', [], _('a specific branch you would like to bundle'),
1296 _('BRANCH')),
1296 _('BRANCH')),
1297 ('', 'base', [],
1297 ('', 'base', [],
1298 _('a base changeset assumed to be available at the destination'),
1298 _('a base changeset assumed to be available at the destination'),
1299 _('REV')),
1299 _('REV')),
1300 ('a', 'all', None, _('bundle all changesets in the repository')),
1300 ('a', 'all', None, _('bundle all changesets in the repository')),
1301 ('t', 'type', 'bzip2', _('bundle compression type to use'), _('TYPE')),
1301 ('t', 'type', 'bzip2', _('bundle compression type to use'), _('TYPE')),
1302 ] + remoteopts,
1302 ] + remoteopts,
1303 _('[-f] [-t TYPE] [-a] [-r REV]... [--base REV]... FILE [DEST]'))
1303 _('[-f] [-t TYPE] [-a] [-r REV]... [--base REV]... FILE [DEST]'))
1304 def bundle(ui, repo, fname, dest=None, **opts):
1304 def bundle(ui, repo, fname, dest=None, **opts):
1305 """create a changegroup file
1305 """create a changegroup file
1306
1306
1307 Generate a changegroup file collecting changesets to be added
1307 Generate a changegroup file collecting changesets to be added
1308 to a repository.
1308 to a repository.
1309
1309
1310 To create a bundle containing all changesets, use -a/--all
1310 To create a bundle containing all changesets, use -a/--all
1311 (or --base null). Otherwise, hg assumes the destination will have
1311 (or --base null). Otherwise, hg assumes the destination will have
1312 all the nodes you specify with --base parameters. Otherwise, hg
1312 all the nodes you specify with --base parameters. Otherwise, hg
1313 will assume the repository has all the nodes in destination, or
1313 will assume the repository has all the nodes in destination, or
1314 default-push/default if no destination is specified.
1314 default-push/default if no destination is specified.
1315
1315
1316 You can change bundle format with the -t/--type option. You can
1316 You can change bundle format with the -t/--type option. You can
1317 specify a compression, a bundle version or both using a dash
1317 specify a compression, a bundle version or both using a dash
1318 (comp-version). The available compression methods are: none, bzip2,
1318 (comp-version). The available compression methods are: none, bzip2,
1319 and gzip (by default, bundles are compressed using bzip2). The
1319 and gzip (by default, bundles are compressed using bzip2). The
1320 available formats are: v1, v2 (default to most suitable).
1320 available formats are: v1, v2 (default to most suitable).
1321
1321
1322 The bundle file can then be transferred using conventional means
1322 The bundle file can then be transferred using conventional means
1323 and applied to another repository with the unbundle or pull
1323 and applied to another repository with the unbundle or pull
1324 command. This is useful when direct push and pull are not
1324 command. This is useful when direct push and pull are not
1325 available or when exporting an entire repository is undesirable.
1325 available or when exporting an entire repository is undesirable.
1326
1326
1327 Applying bundles preserves all changeset contents including
1327 Applying bundles preserves all changeset contents including
1328 permissions, copy/rename information, and revision history.
1328 permissions, copy/rename information, and revision history.
1329
1329
1330 Returns 0 on success, 1 if no changes found.
1330 Returns 0 on success, 1 if no changes found.
1331 """
1331 """
1332 revs = None
1332 revs = None
1333 if 'rev' in opts:
1333 if 'rev' in opts:
1334 revs = scmutil.revrange(repo, opts['rev'])
1334 revs = scmutil.revrange(repo, opts['rev'])
1335
1335
1336 bundletype = opts.get('type', 'bzip2').lower()
1336 bundletype = opts.get('type', 'bzip2').lower()
1337 try:
1337 try:
1338 bcompression, cgversion, params = exchange.parsebundlespec(
1338 bcompression, cgversion, params = exchange.parsebundlespec(
1339 repo, bundletype, strict=False)
1339 repo, bundletype, strict=False)
1340 except error.UnsupportedBundleSpecification as e:
1340 except error.UnsupportedBundleSpecification as e:
1341 raise error.Abort(str(e),
1341 raise error.Abort(str(e),
1342 hint=_('see "hg help bundle" for supported '
1342 hint=_('see "hg help bundle" for supported '
1343 'values for --type'))
1343 'values for --type'))
1344
1344
1345 # Packed bundles are a pseudo bundle format for now.
1345 # Packed bundles are a pseudo bundle format for now.
1346 if cgversion == 's1':
1346 if cgversion == 's1':
1347 raise error.Abort(_('packed bundles cannot be produced by "hg bundle"'),
1347 raise error.Abort(_('packed bundles cannot be produced by "hg bundle"'),
1348 hint=_('use "hg debugcreatestreamclonebundle"'))
1348 hint=_('use "hg debugcreatestreamclonebundle"'))
1349
1349
1350 if opts.get('all'):
1350 if opts.get('all'):
1351 if dest:
1351 if dest:
1352 raise error.Abort(_("--all is incompatible with specifying "
1352 raise error.Abort(_("--all is incompatible with specifying "
1353 "a destination"))
1353 "a destination"))
1354 if opts.get('base'):
1354 if opts.get('base'):
1355 ui.warn(_("ignoring --base because --all was specified\n"))
1355 ui.warn(_("ignoring --base because --all was specified\n"))
1356 base = ['null']
1356 base = ['null']
1357 else:
1357 else:
1358 base = scmutil.revrange(repo, opts.get('base'))
1358 base = scmutil.revrange(repo, opts.get('base'))
1359 # TODO: get desired bundlecaps from command line.
1359 # TODO: get desired bundlecaps from command line.
1360 bundlecaps = None
1360 bundlecaps = None
1361 if base:
1361 if base:
1362 if dest:
1362 if dest:
1363 raise error.Abort(_("--base is incompatible with specifying "
1363 raise error.Abort(_("--base is incompatible with specifying "
1364 "a destination"))
1364 "a destination"))
1365 common = [repo.lookup(rev) for rev in base]
1365 common = [repo.lookup(rev) for rev in base]
1366 heads = revs and map(repo.lookup, revs) or revs
1366 heads = revs and map(repo.lookup, revs) or revs
1367 cg = changegroup.getchangegroup(repo, 'bundle', heads=heads,
1367 cg = changegroup.getchangegroup(repo, 'bundle', heads=heads,
1368 common=common, bundlecaps=bundlecaps,
1368 common=common, bundlecaps=bundlecaps,
1369 version=cgversion)
1369 version=cgversion)
1370 outgoing = None
1370 outgoing = None
1371 else:
1371 else:
1372 dest = ui.expandpath(dest or 'default-push', dest or 'default')
1372 dest = ui.expandpath(dest or 'default-push', dest or 'default')
1373 dest, branches = hg.parseurl(dest, opts.get('branch'))
1373 dest, branches = hg.parseurl(dest, opts.get('branch'))
1374 other = hg.peer(repo, opts, dest)
1374 other = hg.peer(repo, opts, dest)
1375 revs, checkout = hg.addbranchrevs(repo, repo, branches, revs)
1375 revs, checkout = hg.addbranchrevs(repo, repo, branches, revs)
1376 heads = revs and map(repo.lookup, revs) or revs
1376 heads = revs and map(repo.lookup, revs) or revs
1377 outgoing = discovery.findcommonoutgoing(repo, other,
1377 outgoing = discovery.findcommonoutgoing(repo, other,
1378 onlyheads=heads,
1378 onlyheads=heads,
1379 force=opts.get('force'),
1379 force=opts.get('force'),
1380 portable=True)
1380 portable=True)
1381 cg = changegroup.getlocalchangegroup(repo, 'bundle', outgoing,
1381 cg = changegroup.getlocalchangegroup(repo, 'bundle', outgoing,
1382 bundlecaps, version=cgversion)
1382 bundlecaps, version=cgversion)
1383 if not cg:
1383 if not cg:
1384 scmutil.nochangesfound(ui, repo, outgoing and outgoing.excluded)
1384 scmutil.nochangesfound(ui, repo, outgoing and outgoing.excluded)
1385 return 1
1385 return 1
1386
1386
1387 if cgversion == '01': #bundle1
1387 if cgversion == '01': #bundle1
1388 if bcompression is None:
1388 if bcompression is None:
1389 bcompression = 'UN'
1389 bcompression = 'UN'
1390 bversion = 'HG10' + bcompression
1390 bversion = 'HG10' + bcompression
1391 bcompression = None
1391 bcompression = None
1392 else:
1392 else:
1393 assert cgversion == '02'
1393 assert cgversion == '02'
1394 bversion = 'HG20'
1394 bversion = 'HG20'
1395
1395
1396
1396
1397 changegroup.writebundle(ui, cg, fname, bversion, compression=bcompression)
1397 changegroup.writebundle(ui, cg, fname, bversion, compression=bcompression)
1398
1398
1399 @command('cat',
1399 @command('cat',
1400 [('o', 'output', '',
1400 [('o', 'output', '',
1401 _('print output to file with formatted name'), _('FORMAT')),
1401 _('print output to file with formatted name'), _('FORMAT')),
1402 ('r', 'rev', '', _('print the given revision'), _('REV')),
1402 ('r', 'rev', '', _('print the given revision'), _('REV')),
1403 ('', 'decode', None, _('apply any matching decode filter')),
1403 ('', 'decode', None, _('apply any matching decode filter')),
1404 ] + walkopts,
1404 ] + walkopts,
1405 _('[OPTION]... FILE...'),
1405 _('[OPTION]... FILE...'),
1406 inferrepo=True)
1406 inferrepo=True)
1407 def cat(ui, repo, file1, *pats, **opts):
1407 def cat(ui, repo, file1, *pats, **opts):
1408 """output the current or given revision of files
1408 """output the current or given revision of files
1409
1409
1410 Print the specified files as they were at the given revision. If
1410 Print the specified files as they were at the given revision. If
1411 no revision is given, the parent of the working directory is used.
1411 no revision is given, the parent of the working directory is used.
1412
1412
1413 Output may be to a file, in which case the name of the file is
1413 Output may be to a file, in which case the name of the file is
1414 given using a format string. The formatting rules as follows:
1414 given using a format string. The formatting rules as follows:
1415
1415
1416 :``%%``: literal "%" character
1416 :``%%``: literal "%" character
1417 :``%s``: basename of file being printed
1417 :``%s``: basename of file being printed
1418 :``%d``: dirname of file being printed, or '.' if in repository root
1418 :``%d``: dirname of file being printed, or '.' if in repository root
1419 :``%p``: root-relative path name of file being printed
1419 :``%p``: root-relative path name of file being printed
1420 :``%H``: changeset hash (40 hexadecimal digits)
1420 :``%H``: changeset hash (40 hexadecimal digits)
1421 :``%R``: changeset revision number
1421 :``%R``: changeset revision number
1422 :``%h``: short-form changeset hash (12 hexadecimal digits)
1422 :``%h``: short-form changeset hash (12 hexadecimal digits)
1423 :``%r``: zero-padded changeset revision number
1423 :``%r``: zero-padded changeset revision number
1424 :``%b``: basename of the exporting repository
1424 :``%b``: basename of the exporting repository
1425
1425
1426 Returns 0 on success.
1426 Returns 0 on success.
1427 """
1427 """
1428 ctx = scmutil.revsingle(repo, opts.get('rev'))
1428 ctx = scmutil.revsingle(repo, opts.get('rev'))
1429 m = scmutil.match(ctx, (file1,) + pats, opts)
1429 m = scmutil.match(ctx, (file1,) + pats, opts)
1430
1430
1431 return cmdutil.cat(ui, repo, ctx, m, '', **opts)
1431 return cmdutil.cat(ui, repo, ctx, m, '', **opts)
1432
1432
1433 @command('^clone',
1433 @command('^clone',
1434 [('U', 'noupdate', None, _('the clone will include an empty working '
1434 [('U', 'noupdate', None, _('the clone will include an empty working '
1435 'directory (only a repository)')),
1435 'directory (only a repository)')),
1436 ('u', 'updaterev', '', _('revision, tag, or branch to check out'),
1436 ('u', 'updaterev', '', _('revision, tag, or branch to check out'),
1437 _('REV')),
1437 _('REV')),
1438 ('r', 'rev', [], _('include the specified changeset'), _('REV')),
1438 ('r', 'rev', [], _('include the specified changeset'), _('REV')),
1439 ('b', 'branch', [], _('clone only the specified branch'), _('BRANCH')),
1439 ('b', 'branch', [], _('clone only the specified branch'), _('BRANCH')),
1440 ('', 'pull', None, _('use pull protocol to copy metadata')),
1440 ('', 'pull', None, _('use pull protocol to copy metadata')),
1441 ('', 'uncompressed', None, _('use uncompressed transfer (fast over LAN)')),
1441 ('', 'uncompressed', None, _('use uncompressed transfer (fast over LAN)')),
1442 ] + remoteopts,
1442 ] + remoteopts,
1443 _('[OPTION]... SOURCE [DEST]'),
1443 _('[OPTION]... SOURCE [DEST]'),
1444 norepo=True)
1444 norepo=True)
1445 def clone(ui, source, dest=None, **opts):
1445 def clone(ui, source, dest=None, **opts):
1446 """make a copy of an existing repository
1446 """make a copy of an existing repository
1447
1447
1448 Create a copy of an existing repository in a new directory.
1448 Create a copy of an existing repository in a new directory.
1449
1449
1450 If no destination directory name is specified, it defaults to the
1450 If no destination directory name is specified, it defaults to the
1451 basename of the source.
1451 basename of the source.
1452
1452
1453 The location of the source is added to the new repository's
1453 The location of the source is added to the new repository's
1454 ``.hg/hgrc`` file, as the default to be used for future pulls.
1454 ``.hg/hgrc`` file, as the default to be used for future pulls.
1455
1455
1456 Only local paths and ``ssh://`` URLs are supported as
1456 Only local paths and ``ssh://`` URLs are supported as
1457 destinations. For ``ssh://`` destinations, no working directory or
1457 destinations. For ``ssh://`` destinations, no working directory or
1458 ``.hg/hgrc`` will be created on the remote side.
1458 ``.hg/hgrc`` will be created on the remote side.
1459
1459
1460 If the source repository has a bookmark called '@' set, that
1460 If the source repository has a bookmark called '@' set, that
1461 revision will be checked out in the new repository by default.
1461 revision will be checked out in the new repository by default.
1462
1462
1463 To check out a particular version, use -u/--update, or
1463 To check out a particular version, use -u/--update, or
1464 -U/--noupdate to create a clone with no working directory.
1464 -U/--noupdate to create a clone with no working directory.
1465
1465
1466 To pull only a subset of changesets, specify one or more revisions
1466 To pull only a subset of changesets, specify one or more revisions
1467 identifiers with -r/--rev or branches with -b/--branch. The
1467 identifiers with -r/--rev or branches with -b/--branch. The
1468 resulting clone will contain only the specified changesets and
1468 resulting clone will contain only the specified changesets and
1469 their ancestors. These options (or 'clone src#rev dest') imply
1469 their ancestors. These options (or 'clone src#rev dest') imply
1470 --pull, even for local source repositories.
1470 --pull, even for local source repositories.
1471
1471
1472 .. note::
1472 .. note::
1473
1473
1474 Specifying a tag will include the tagged changeset but not the
1474 Specifying a tag will include the tagged changeset but not the
1475 changeset containing the tag.
1475 changeset containing the tag.
1476
1476
1477 .. container:: verbose
1477 .. container:: verbose
1478
1478
1479 For efficiency, hardlinks are used for cloning whenever the
1479 For efficiency, hardlinks are used for cloning whenever the
1480 source and destination are on the same filesystem (note this
1480 source and destination are on the same filesystem (note this
1481 applies only to the repository data, not to the working
1481 applies only to the repository data, not to the working
1482 directory). Some filesystems, such as AFS, implement hardlinking
1482 directory). Some filesystems, such as AFS, implement hardlinking
1483 incorrectly, but do not report errors. In these cases, use the
1483 incorrectly, but do not report errors. In these cases, use the
1484 --pull option to avoid hardlinking.
1484 --pull option to avoid hardlinking.
1485
1485
1486 In some cases, you can clone repositories and the working
1486 In some cases, you can clone repositories and the working
1487 directory using full hardlinks with ::
1487 directory using full hardlinks with ::
1488
1488
1489 $ cp -al REPO REPOCLONE
1489 $ cp -al REPO REPOCLONE
1490
1490
1491 This is the fastest way to clone, but it is not always safe. The
1491 This is the fastest way to clone, but it is not always safe. The
1492 operation is not atomic (making sure REPO is not modified during
1492 operation is not atomic (making sure REPO is not modified during
1493 the operation is up to you) and you have to make sure your
1493 the operation is up to you) and you have to make sure your
1494 editor breaks hardlinks (Emacs and most Linux Kernel tools do
1494 editor breaks hardlinks (Emacs and most Linux Kernel tools do
1495 so). Also, this is not compatible with certain extensions that
1495 so). Also, this is not compatible with certain extensions that
1496 place their metadata under the .hg directory, such as mq.
1496 place their metadata under the .hg directory, such as mq.
1497
1497
1498 Mercurial will update the working directory to the first applicable
1498 Mercurial will update the working directory to the first applicable
1499 revision from this list:
1499 revision from this list:
1500
1500
1501 a) null if -U or the source repository has no changesets
1501 a) null if -U or the source repository has no changesets
1502 b) if -u . and the source repository is local, the first parent of
1502 b) if -u . and the source repository is local, the first parent of
1503 the source repository's working directory
1503 the source repository's working directory
1504 c) the changeset specified with -u (if a branch name, this means the
1504 c) the changeset specified with -u (if a branch name, this means the
1505 latest head of that branch)
1505 latest head of that branch)
1506 d) the changeset specified with -r
1506 d) the changeset specified with -r
1507 e) the tipmost head specified with -b
1507 e) the tipmost head specified with -b
1508 f) the tipmost head specified with the url#branch source syntax
1508 f) the tipmost head specified with the url#branch source syntax
1509 g) the revision marked with the '@' bookmark, if present
1509 g) the revision marked with the '@' bookmark, if present
1510 h) the tipmost head of the default branch
1510 h) the tipmost head of the default branch
1511 i) tip
1511 i) tip
1512
1512
1513 Examples:
1513 Examples:
1514
1514
1515 - clone a remote repository to a new directory named hg/::
1515 - clone a remote repository to a new directory named hg/::
1516
1516
1517 hg clone http://selenic.com/hg
1517 hg clone http://selenic.com/hg
1518
1518
1519 - create a lightweight local clone::
1519 - create a lightweight local clone::
1520
1520
1521 hg clone project/ project-feature/
1521 hg clone project/ project-feature/
1522
1522
1523 - clone from an absolute path on an ssh server (note double-slash)::
1523 - clone from an absolute path on an ssh server (note double-slash)::
1524
1524
1525 hg clone ssh://user@server//home/projects/alpha/
1525 hg clone ssh://user@server//home/projects/alpha/
1526
1526
1527 - do a high-speed clone over a LAN while checking out a
1527 - do a high-speed clone over a LAN while checking out a
1528 specified version::
1528 specified version::
1529
1529
1530 hg clone --uncompressed http://server/repo -u 1.5
1530 hg clone --uncompressed http://server/repo -u 1.5
1531
1531
1532 - create a repository without changesets after a particular revision::
1532 - create a repository without changesets after a particular revision::
1533
1533
1534 hg clone -r 04e544 experimental/ good/
1534 hg clone -r 04e544 experimental/ good/
1535
1535
1536 - clone (and track) a particular named branch::
1536 - clone (and track) a particular named branch::
1537
1537
1538 hg clone http://selenic.com/hg#stable
1538 hg clone http://selenic.com/hg#stable
1539
1539
1540 See :hg:`help urls` for details on specifying URLs.
1540 See :hg:`help urls` for details on specifying URLs.
1541
1541
1542 Returns 0 on success.
1542 Returns 0 on success.
1543 """
1543 """
1544 if opts.get('noupdate') and opts.get('updaterev'):
1544 if opts.get('noupdate') and opts.get('updaterev'):
1545 raise error.Abort(_("cannot specify both --noupdate and --updaterev"))
1545 raise error.Abort(_("cannot specify both --noupdate and --updaterev"))
1546
1546
1547 r = hg.clone(ui, opts, source, dest,
1547 r = hg.clone(ui, opts, source, dest,
1548 pull=opts.get('pull'),
1548 pull=opts.get('pull'),
1549 stream=opts.get('uncompressed'),
1549 stream=opts.get('uncompressed'),
1550 rev=opts.get('rev'),
1550 rev=opts.get('rev'),
1551 update=opts.get('updaterev') or not opts.get('noupdate'),
1551 update=opts.get('updaterev') or not opts.get('noupdate'),
1552 branch=opts.get('branch'),
1552 branch=opts.get('branch'),
1553 shareopts=opts.get('shareopts'))
1553 shareopts=opts.get('shareopts'))
1554
1554
1555 return r is None
1555 return r is None
1556
1556
1557 @command('^commit|ci',
1557 @command('^commit|ci',
1558 [('A', 'addremove', None,
1558 [('A', 'addremove', None,
1559 _('mark new/missing files as added/removed before committing')),
1559 _('mark new/missing files as added/removed before committing')),
1560 ('', 'close-branch', None,
1560 ('', 'close-branch', None,
1561 _('mark a branch head as closed')),
1561 _('mark a branch head as closed')),
1562 ('', 'amend', None, _('amend the parent of the working directory')),
1562 ('', 'amend', None, _('amend the parent of the working directory')),
1563 ('s', 'secret', None, _('use the secret phase for committing')),
1563 ('s', 'secret', None, _('use the secret phase for committing')),
1564 ('e', 'edit', None, _('invoke editor on commit messages')),
1564 ('e', 'edit', None, _('invoke editor on commit messages')),
1565 ('i', 'interactive', None, _('use interactive mode')),
1565 ('i', 'interactive', None, _('use interactive mode')),
1566 ] + walkopts + commitopts + commitopts2 + subrepoopts,
1566 ] + walkopts + commitopts + commitopts2 + subrepoopts,
1567 _('[OPTION]... [FILE]...'),
1567 _('[OPTION]... [FILE]...'),
1568 inferrepo=True)
1568 inferrepo=True)
1569 def commit(ui, repo, *pats, **opts):
1569 def commit(ui, repo, *pats, **opts):
1570 """commit the specified files or all outstanding changes
1570 """commit the specified files or all outstanding changes
1571
1571
1572 Commit changes to the given files into the repository. Unlike a
1572 Commit changes to the given files into the repository. Unlike a
1573 centralized SCM, this operation is a local operation. See
1573 centralized SCM, this operation is a local operation. See
1574 :hg:`push` for a way to actively distribute your changes.
1574 :hg:`push` for a way to actively distribute your changes.
1575
1575
1576 If a list of files is omitted, all changes reported by :hg:`status`
1576 If a list of files is omitted, all changes reported by :hg:`status`
1577 will be committed.
1577 will be committed.
1578
1578
1579 If you are committing the result of a merge, do not provide any
1579 If you are committing the result of a merge, do not provide any
1580 filenames or -I/-X filters.
1580 filenames or -I/-X filters.
1581
1581
1582 If no commit message is specified, Mercurial starts your
1582 If no commit message is specified, Mercurial starts your
1583 configured editor where you can enter a message. In case your
1583 configured editor where you can enter a message. In case your
1584 commit fails, you will find a backup of your message in
1584 commit fails, you will find a backup of your message in
1585 ``.hg/last-message.txt``.
1585 ``.hg/last-message.txt``.
1586
1586
1587 The --close-branch flag can be used to mark the current branch
1587 The --close-branch flag can be used to mark the current branch
1588 head closed. When all heads of a branch are closed, the branch
1588 head closed. When all heads of a branch are closed, the branch
1589 will be considered closed and no longer listed.
1589 will be considered closed and no longer listed.
1590
1590
1591 The --amend flag can be used to amend the parent of the
1591 The --amend flag can be used to amend the parent of the
1592 working directory with a new commit that contains the changes
1592 working directory with a new commit that contains the changes
1593 in the parent in addition to those currently reported by :hg:`status`,
1593 in the parent in addition to those currently reported by :hg:`status`,
1594 if there are any. The old commit is stored in a backup bundle in
1594 if there are any. The old commit is stored in a backup bundle in
1595 ``.hg/strip-backup`` (see :hg:`help bundle` and :hg:`help unbundle`
1595 ``.hg/strip-backup`` (see :hg:`help bundle` and :hg:`help unbundle`
1596 on how to restore it).
1596 on how to restore it).
1597
1597
1598 Message, user and date are taken from the amended commit unless
1598 Message, user and date are taken from the amended commit unless
1599 specified. When a message isn't specified on the command line,
1599 specified. When a message isn't specified on the command line,
1600 the editor will open with the message of the amended commit.
1600 the editor will open with the message of the amended commit.
1601
1601
1602 It is not possible to amend public changesets (see :hg:`help phases`)
1602 It is not possible to amend public changesets (see :hg:`help phases`)
1603 or changesets that have children.
1603 or changesets that have children.
1604
1604
1605 See :hg:`help dates` for a list of formats valid for -d/--date.
1605 See :hg:`help dates` for a list of formats valid for -d/--date.
1606
1606
1607 Returns 0 on success, 1 if nothing changed.
1607 Returns 0 on success, 1 if nothing changed.
1608
1608
1609 .. container:: verbose
1609 .. container:: verbose
1610
1610
1611 Examples:
1611 Examples:
1612
1612
1613 - commit all files ending in .py::
1613 - commit all files ending in .py::
1614
1614
1615 hg commit --include "set:**.py"
1615 hg commit --include "set:**.py"
1616
1616
1617 - commit all non-binary files::
1617 - commit all non-binary files::
1618
1618
1619 hg commit --exclude "set:binary()"
1619 hg commit --exclude "set:binary()"
1620
1620
1621 - amend the current commit and set the date to now::
1621 - amend the current commit and set the date to now::
1622
1622
1623 hg commit --amend --date now
1623 hg commit --amend --date now
1624 """
1624 """
1625 wlock = lock = None
1625 wlock = lock = None
1626 try:
1626 try:
1627 wlock = repo.wlock()
1627 wlock = repo.wlock()
1628 lock = repo.lock()
1628 lock = repo.lock()
1629 return _docommit(ui, repo, *pats, **opts)
1629 return _docommit(ui, repo, *pats, **opts)
1630 finally:
1630 finally:
1631 release(lock, wlock)
1631 release(lock, wlock)
1632
1632
1633 def _docommit(ui, repo, *pats, **opts):
1633 def _docommit(ui, repo, *pats, **opts):
1634 if opts.get('interactive'):
1634 if opts.get('interactive'):
1635 opts.pop('interactive')
1635 opts.pop('interactive')
1636 cmdutil.dorecord(ui, repo, commit, None, False,
1636 cmdutil.dorecord(ui, repo, commit, None, False,
1637 cmdutil.recordfilter, *pats, **opts)
1637 cmdutil.recordfilter, *pats, **opts)
1638 return
1638 return
1639
1639
1640 if opts.get('subrepos'):
1640 if opts.get('subrepos'):
1641 if opts.get('amend'):
1641 if opts.get('amend'):
1642 raise error.Abort(_('cannot amend with --subrepos'))
1642 raise error.Abort(_('cannot amend with --subrepos'))
1643 # Let --subrepos on the command line override config setting.
1643 # Let --subrepos on the command line override config setting.
1644 ui.setconfig('ui', 'commitsubrepos', True, 'commit')
1644 ui.setconfig('ui', 'commitsubrepos', True, 'commit')
1645
1645
1646 cmdutil.checkunfinished(repo, commit=True)
1646 cmdutil.checkunfinished(repo, commit=True)
1647
1647
1648 branch = repo[None].branch()
1648 branch = repo[None].branch()
1649 bheads = repo.branchheads(branch)
1649 bheads = repo.branchheads(branch)
1650
1650
1651 extra = {}
1651 extra = {}
1652 if opts.get('close_branch'):
1652 if opts.get('close_branch'):
1653 extra['close'] = 1
1653 extra['close'] = 1
1654
1654
1655 if not bheads:
1655 if not bheads:
1656 raise error.Abort(_('can only close branch heads'))
1656 raise error.Abort(_('can only close branch heads'))
1657 elif opts.get('amend'):
1657 elif opts.get('amend'):
1658 if repo[None].parents()[0].p1().branch() != branch and \
1658 if repo[None].parents()[0].p1().branch() != branch and \
1659 repo[None].parents()[0].p2().branch() != branch:
1659 repo[None].parents()[0].p2().branch() != branch:
1660 raise error.Abort(_('can only close branch heads'))
1660 raise error.Abort(_('can only close branch heads'))
1661
1661
1662 if opts.get('amend'):
1662 if opts.get('amend'):
1663 if ui.configbool('ui', 'commitsubrepos'):
1663 if ui.configbool('ui', 'commitsubrepos'):
1664 raise error.Abort(_('cannot amend with ui.commitsubrepos enabled'))
1664 raise error.Abort(_('cannot amend with ui.commitsubrepos enabled'))
1665
1665
1666 old = repo['.']
1666 old = repo['.']
1667 if not old.mutable():
1667 if not old.mutable():
1668 raise error.Abort(_('cannot amend public changesets'))
1668 raise error.Abort(_('cannot amend public changesets'))
1669 if len(repo[None].parents()) > 1:
1669 if len(repo[None].parents()) > 1:
1670 raise error.Abort(_('cannot amend while merging'))
1670 raise error.Abort(_('cannot amend while merging'))
1671 allowunstable = obsolete.isenabled(repo, obsolete.allowunstableopt)
1671 allowunstable = obsolete.isenabled(repo, obsolete.allowunstableopt)
1672 if not allowunstable and old.children():
1672 if not allowunstable and old.children():
1673 raise error.Abort(_('cannot amend changeset with children'))
1673 raise error.Abort(_('cannot amend changeset with children'))
1674
1674
1675 newextra = extra.copy()
1675 newextra = extra.copy()
1676 newextra['branch'] = branch
1676 newextra['branch'] = branch
1677 extra = newextra
1677 extra = newextra
1678 # commitfunc is used only for temporary amend commit by cmdutil.amend
1678 # commitfunc is used only for temporary amend commit by cmdutil.amend
1679 def commitfunc(ui, repo, message, match, opts):
1679 def commitfunc(ui, repo, message, match, opts):
1680 return repo.commit(message,
1680 return repo.commit(message,
1681 opts.get('user') or old.user(),
1681 opts.get('user') or old.user(),
1682 opts.get('date') or old.date(),
1682 opts.get('date') or old.date(),
1683 match,
1683 match,
1684 extra=extra)
1684 extra=extra)
1685
1685
1686 node = cmdutil.amend(ui, repo, commitfunc, old, extra, pats, opts)
1686 node = cmdutil.amend(ui, repo, commitfunc, old, extra, pats, opts)
1687 if node == old.node():
1687 if node == old.node():
1688 ui.status(_("nothing changed\n"))
1688 ui.status(_("nothing changed\n"))
1689 return 1
1689 return 1
1690 else:
1690 else:
1691 def commitfunc(ui, repo, message, match, opts):
1691 def commitfunc(ui, repo, message, match, opts):
1692 backup = ui.backupconfig('phases', 'new-commit')
1692 backup = ui.backupconfig('phases', 'new-commit')
1693 baseui = repo.baseui
1693 baseui = repo.baseui
1694 basebackup = baseui.backupconfig('phases', 'new-commit')
1694 basebackup = baseui.backupconfig('phases', 'new-commit')
1695 try:
1695 try:
1696 if opts.get('secret'):
1696 if opts.get('secret'):
1697 ui.setconfig('phases', 'new-commit', 'secret', 'commit')
1697 ui.setconfig('phases', 'new-commit', 'secret', 'commit')
1698 # Propagate to subrepos
1698 # Propagate to subrepos
1699 baseui.setconfig('phases', 'new-commit', 'secret', 'commit')
1699 baseui.setconfig('phases', 'new-commit', 'secret', 'commit')
1700
1700
1701 editform = cmdutil.mergeeditform(repo[None], 'commit.normal')
1701 editform = cmdutil.mergeeditform(repo[None], 'commit.normal')
1702 editor = cmdutil.getcommiteditor(editform=editform, **opts)
1702 editor = cmdutil.getcommiteditor(editform=editform, **opts)
1703 return repo.commit(message, opts.get('user'), opts.get('date'),
1703 return repo.commit(message, opts.get('user'), opts.get('date'),
1704 match,
1704 match,
1705 editor=editor,
1705 editor=editor,
1706 extra=extra)
1706 extra=extra)
1707 finally:
1707 finally:
1708 ui.restoreconfig(backup)
1708 ui.restoreconfig(backup)
1709 repo.baseui.restoreconfig(basebackup)
1709 repo.baseui.restoreconfig(basebackup)
1710
1710
1711
1711
1712 node = cmdutil.commit(ui, repo, commitfunc, pats, opts)
1712 node = cmdutil.commit(ui, repo, commitfunc, pats, opts)
1713
1713
1714 if not node:
1714 if not node:
1715 stat = repo.status(match=scmutil.match(repo[None], pats, opts))
1715 stat = repo.status(match=scmutil.match(repo[None], pats, opts))
1716 if stat[3]:
1716 if stat[3]:
1717 ui.status(_("nothing changed (%d missing files, see "
1717 ui.status(_("nothing changed (%d missing files, see "
1718 "'hg status')\n") % len(stat[3]))
1718 "'hg status')\n") % len(stat[3]))
1719 else:
1719 else:
1720 ui.status(_("nothing changed\n"))
1720 ui.status(_("nothing changed\n"))
1721 return 1
1721 return 1
1722
1722
1723 cmdutil.commitstatus(repo, node, branch, bheads, opts)
1723 cmdutil.commitstatus(repo, node, branch, bheads, opts)
1724
1724
1725 @command('config|showconfig|debugconfig',
1725 @command('config|showconfig|debugconfig',
1726 [('u', 'untrusted', None, _('show untrusted configuration options')),
1726 [('u', 'untrusted', None, _('show untrusted configuration options')),
1727 ('e', 'edit', None, _('edit user config')),
1727 ('e', 'edit', None, _('edit user config')),
1728 ('l', 'local', None, _('edit repository config')),
1728 ('l', 'local', None, _('edit repository config')),
1729 ('g', 'global', None, _('edit global config'))],
1729 ('g', 'global', None, _('edit global config'))],
1730 _('[-u] [NAME]...'),
1730 _('[-u] [NAME]...'),
1731 optionalrepo=True)
1731 optionalrepo=True)
1732 def config(ui, repo, *values, **opts):
1732 def config(ui, repo, *values, **opts):
1733 """show combined config settings from all hgrc files
1733 """show combined config settings from all hgrc files
1734
1734
1735 With no arguments, print names and values of all config items.
1735 With no arguments, print names and values of all config items.
1736
1736
1737 With one argument of the form section.name, print just the value
1737 With one argument of the form section.name, print just the value
1738 of that config item.
1738 of that config item.
1739
1739
1740 With multiple arguments, print names and values of all config
1740 With multiple arguments, print names and values of all config
1741 items with matching section names.
1741 items with matching section names.
1742
1742
1743 With --edit, start an editor on the user-level config file. With
1743 With --edit, start an editor on the user-level config file. With
1744 --global, edit the system-wide config file. With --local, edit the
1744 --global, edit the system-wide config file. With --local, edit the
1745 repository-level config file.
1745 repository-level config file.
1746
1746
1747 With --debug, the source (filename and line number) is printed
1747 With --debug, the source (filename and line number) is printed
1748 for each config item.
1748 for each config item.
1749
1749
1750 See :hg:`help config` for more information about config files.
1750 See :hg:`help config` for more information about config files.
1751
1751
1752 Returns 0 on success, 1 if NAME does not exist.
1752 Returns 0 on success, 1 if NAME does not exist.
1753
1753
1754 """
1754 """
1755
1755
1756 if opts.get('edit') or opts.get('local') or opts.get('global'):
1756 if opts.get('edit') or opts.get('local') or opts.get('global'):
1757 if opts.get('local') and opts.get('global'):
1757 if opts.get('local') and opts.get('global'):
1758 raise error.Abort(_("can't use --local and --global together"))
1758 raise error.Abort(_("can't use --local and --global together"))
1759
1759
1760 if opts.get('local'):
1760 if opts.get('local'):
1761 if not repo:
1761 if not repo:
1762 raise error.Abort(_("can't use --local outside a repository"))
1762 raise error.Abort(_("can't use --local outside a repository"))
1763 paths = [repo.join('hgrc')]
1763 paths = [repo.join('hgrc')]
1764 elif opts.get('global'):
1764 elif opts.get('global'):
1765 paths = scmutil.systemrcpath()
1765 paths = scmutil.systemrcpath()
1766 else:
1766 else:
1767 paths = scmutil.userrcpath()
1767 paths = scmutil.userrcpath()
1768
1768
1769 for f in paths:
1769 for f in paths:
1770 if os.path.exists(f):
1770 if os.path.exists(f):
1771 break
1771 break
1772 else:
1772 else:
1773 if opts.get('global'):
1773 if opts.get('global'):
1774 samplehgrc = uimod.samplehgrcs['global']
1774 samplehgrc = uimod.samplehgrcs['global']
1775 elif opts.get('local'):
1775 elif opts.get('local'):
1776 samplehgrc = uimod.samplehgrcs['local']
1776 samplehgrc = uimod.samplehgrcs['local']
1777 else:
1777 else:
1778 samplehgrc = uimod.samplehgrcs['user']
1778 samplehgrc = uimod.samplehgrcs['user']
1779
1779
1780 f = paths[0]
1780 f = paths[0]
1781 fp = open(f, "w")
1781 fp = open(f, "w")
1782 fp.write(samplehgrc)
1782 fp.write(samplehgrc)
1783 fp.close()
1783 fp.close()
1784
1784
1785 editor = ui.geteditor()
1785 editor = ui.geteditor()
1786 ui.system("%s \"%s\"" % (editor, f),
1786 ui.system("%s \"%s\"" % (editor, f),
1787 onerr=error.Abort, errprefix=_("edit failed"))
1787 onerr=error.Abort, errprefix=_("edit failed"))
1788 return
1788 return
1789
1789
1790 for f in scmutil.rcpath():
1790 for f in scmutil.rcpath():
1791 ui.debug('read config from: %s\n' % f)
1791 ui.debug('read config from: %s\n' % f)
1792 untrusted = bool(opts.get('untrusted'))
1792 untrusted = bool(opts.get('untrusted'))
1793 if values:
1793 if values:
1794 sections = [v for v in values if '.' not in v]
1794 sections = [v for v in values if '.' not in v]
1795 items = [v for v in values if '.' in v]
1795 items = [v for v in values if '.' in v]
1796 if len(items) > 1 or items and sections:
1796 if len(items) > 1 or items and sections:
1797 raise error.Abort(_('only one config item permitted'))
1797 raise error.Abort(_('only one config item permitted'))
1798 matched = False
1798 matched = False
1799 for section, name, value in ui.walkconfig(untrusted=untrusted):
1799 for section, name, value in ui.walkconfig(untrusted=untrusted):
1800 value = str(value).replace('\n', '\\n')
1800 value = str(value).replace('\n', '\\n')
1801 sectname = section + '.' + name
1801 sectname = section + '.' + name
1802 if values:
1802 if values:
1803 for v in values:
1803 for v in values:
1804 if v == section:
1804 if v == section:
1805 ui.debug('%s: ' %
1805 ui.debug('%s: ' %
1806 ui.configsource(section, name, untrusted))
1806 ui.configsource(section, name, untrusted))
1807 ui.write('%s=%s\n' % (sectname, value))
1807 ui.write('%s=%s\n' % (sectname, value))
1808 matched = True
1808 matched = True
1809 elif v == sectname:
1809 elif v == sectname:
1810 ui.debug('%s: ' %
1810 ui.debug('%s: ' %
1811 ui.configsource(section, name, untrusted))
1811 ui.configsource(section, name, untrusted))
1812 ui.write(value, '\n')
1812 ui.write(value, '\n')
1813 matched = True
1813 matched = True
1814 else:
1814 else:
1815 ui.debug('%s: ' %
1815 ui.debug('%s: ' %
1816 ui.configsource(section, name, untrusted))
1816 ui.configsource(section, name, untrusted))
1817 ui.write('%s=%s\n' % (sectname, value))
1817 ui.write('%s=%s\n' % (sectname, value))
1818 matched = True
1818 matched = True
1819 if matched:
1819 if matched:
1820 return 0
1820 return 0
1821 return 1
1821 return 1
1822
1822
1823 @command('copy|cp',
1823 @command('copy|cp',
1824 [('A', 'after', None, _('record a copy that has already occurred')),
1824 [('A', 'after', None, _('record a copy that has already occurred')),
1825 ('f', 'force', None, _('forcibly copy over an existing managed file')),
1825 ('f', 'force', None, _('forcibly copy over an existing managed file')),
1826 ] + walkopts + dryrunopts,
1826 ] + walkopts + dryrunopts,
1827 _('[OPTION]... [SOURCE]... DEST'))
1827 _('[OPTION]... [SOURCE]... DEST'))
1828 def copy(ui, repo, *pats, **opts):
1828 def copy(ui, repo, *pats, **opts):
1829 """mark files as copied for the next commit
1829 """mark files as copied for the next commit
1830
1830
1831 Mark dest as having copies of source files. If dest is a
1831 Mark dest as having copies of source files. If dest is a
1832 directory, copies are put in that directory. If dest is a file,
1832 directory, copies are put in that directory. If dest is a file,
1833 the source must be a single file.
1833 the source must be a single file.
1834
1834
1835 By default, this command copies the contents of files as they
1835 By default, this command copies the contents of files as they
1836 exist in the working directory. If invoked with -A/--after, the
1836 exist in the working directory. If invoked with -A/--after, the
1837 operation is recorded, but no copying is performed.
1837 operation is recorded, but no copying is performed.
1838
1838
1839 This command takes effect with the next commit. To undo a copy
1839 This command takes effect with the next commit. To undo a copy
1840 before that, see :hg:`revert`.
1840 before that, see :hg:`revert`.
1841
1841
1842 Returns 0 on success, 1 if errors are encountered.
1842 Returns 0 on success, 1 if errors are encountered.
1843 """
1843 """
1844 wlock = repo.wlock(False)
1844 wlock = repo.wlock(False)
1845 try:
1845 try:
1846 return cmdutil.copy(ui, repo, pats, opts)
1846 return cmdutil.copy(ui, repo, pats, opts)
1847 finally:
1847 finally:
1848 wlock.release()
1848 wlock.release()
1849
1849
1850 @command('debugancestor', [], _('[INDEX] REV1 REV2'), optionalrepo=True)
1850 @command('debugancestor', [], _('[INDEX] REV1 REV2'), optionalrepo=True)
1851 def debugancestor(ui, repo, *args):
1851 def debugancestor(ui, repo, *args):
1852 """find the ancestor revision of two revisions in a given index"""
1852 """find the ancestor revision of two revisions in a given index"""
1853 if len(args) == 3:
1853 if len(args) == 3:
1854 index, rev1, rev2 = args
1854 index, rev1, rev2 = args
1855 r = revlog.revlog(scmutil.opener(os.getcwd(), audit=False), index)
1855 r = revlog.revlog(scmutil.opener(os.getcwd(), audit=False), index)
1856 lookup = r.lookup
1856 lookup = r.lookup
1857 elif len(args) == 2:
1857 elif len(args) == 2:
1858 if not repo:
1858 if not repo:
1859 raise error.Abort(_("there is no Mercurial repository here "
1859 raise error.Abort(_("there is no Mercurial repository here "
1860 "(.hg not found)"))
1860 "(.hg not found)"))
1861 rev1, rev2 = args
1861 rev1, rev2 = args
1862 r = repo.changelog
1862 r = repo.changelog
1863 lookup = repo.lookup
1863 lookup = repo.lookup
1864 else:
1864 else:
1865 raise error.Abort(_('either two or three arguments required'))
1865 raise error.Abort(_('either two or three arguments required'))
1866 a = r.ancestor(lookup(rev1), lookup(rev2))
1866 a = r.ancestor(lookup(rev1), lookup(rev2))
1867 ui.write("%d:%s\n" % (r.rev(a), hex(a)))
1867 ui.write("%d:%s\n" % (r.rev(a), hex(a)))
1868
1868
1869 @command('debugbuilddag',
1869 @command('debugbuilddag',
1870 [('m', 'mergeable-file', None, _('add single file mergeable changes')),
1870 [('m', 'mergeable-file', None, _('add single file mergeable changes')),
1871 ('o', 'overwritten-file', None, _('add single file all revs overwrite')),
1871 ('o', 'overwritten-file', None, _('add single file all revs overwrite')),
1872 ('n', 'new-file', None, _('add new file at each rev'))],
1872 ('n', 'new-file', None, _('add new file at each rev'))],
1873 _('[OPTION]... [TEXT]'))
1873 _('[OPTION]... [TEXT]'))
1874 def debugbuilddag(ui, repo, text=None,
1874 def debugbuilddag(ui, repo, text=None,
1875 mergeable_file=False,
1875 mergeable_file=False,
1876 overwritten_file=False,
1876 overwritten_file=False,
1877 new_file=False):
1877 new_file=False):
1878 """builds a repo with a given DAG from scratch in the current empty repo
1878 """builds a repo with a given DAG from scratch in the current empty repo
1879
1879
1880 The description of the DAG is read from stdin if not given on the
1880 The description of the DAG is read from stdin if not given on the
1881 command line.
1881 command line.
1882
1882
1883 Elements:
1883 Elements:
1884
1884
1885 - "+n" is a linear run of n nodes based on the current default parent
1885 - "+n" is a linear run of n nodes based on the current default parent
1886 - "." is a single node based on the current default parent
1886 - "." is a single node based on the current default parent
1887 - "$" resets the default parent to null (implied at the start);
1887 - "$" resets the default parent to null (implied at the start);
1888 otherwise the default parent is always the last node created
1888 otherwise the default parent is always the last node created
1889 - "<p" sets the default parent to the backref p
1889 - "<p" sets the default parent to the backref p
1890 - "*p" is a fork at parent p, which is a backref
1890 - "*p" is a fork at parent p, which is a backref
1891 - "*p1/p2" is a merge of parents p1 and p2, which are backrefs
1891 - "*p1/p2" is a merge of parents p1 and p2, which are backrefs
1892 - "/p2" is a merge of the preceding node and p2
1892 - "/p2" is a merge of the preceding node and p2
1893 - ":tag" defines a local tag for the preceding node
1893 - ":tag" defines a local tag for the preceding node
1894 - "@branch" sets the named branch for subsequent nodes
1894 - "@branch" sets the named branch for subsequent nodes
1895 - "#...\\n" is a comment up to the end of the line
1895 - "#...\\n" is a comment up to the end of the line
1896
1896
1897 Whitespace between the above elements is ignored.
1897 Whitespace between the above elements is ignored.
1898
1898
1899 A backref is either
1899 A backref is either
1900
1900
1901 - a number n, which references the node curr-n, where curr is the current
1901 - a number n, which references the node curr-n, where curr is the current
1902 node, or
1902 node, or
1903 - the name of a local tag you placed earlier using ":tag", or
1903 - the name of a local tag you placed earlier using ":tag", or
1904 - empty to denote the default parent.
1904 - empty to denote the default parent.
1905
1905
1906 All string valued-elements are either strictly alphanumeric, or must
1906 All string valued-elements are either strictly alphanumeric, or must
1907 be enclosed in double quotes ("..."), with "\\" as escape character.
1907 be enclosed in double quotes ("..."), with "\\" as escape character.
1908 """
1908 """
1909
1909
1910 if text is None:
1910 if text is None:
1911 ui.status(_("reading DAG from stdin\n"))
1911 ui.status(_("reading DAG from stdin\n"))
1912 text = ui.fin.read()
1912 text = ui.fin.read()
1913
1913
1914 cl = repo.changelog
1914 cl = repo.changelog
1915 if len(cl) > 0:
1915 if len(cl) > 0:
1916 raise error.Abort(_('repository is not empty'))
1916 raise error.Abort(_('repository is not empty'))
1917
1917
1918 # determine number of revs in DAG
1918 # determine number of revs in DAG
1919 total = 0
1919 total = 0
1920 for type, data in dagparser.parsedag(text):
1920 for type, data in dagparser.parsedag(text):
1921 if type == 'n':
1921 if type == 'n':
1922 total += 1
1922 total += 1
1923
1923
1924 if mergeable_file:
1924 if mergeable_file:
1925 linesperrev = 2
1925 linesperrev = 2
1926 # make a file with k lines per rev
1926 # make a file with k lines per rev
1927 initialmergedlines = [str(i) for i in xrange(0, total * linesperrev)]
1927 initialmergedlines = [str(i) for i in xrange(0, total * linesperrev)]
1928 initialmergedlines.append("")
1928 initialmergedlines.append("")
1929
1929
1930 tags = []
1930 tags = []
1931
1931
1932 lock = tr = None
1932 lock = tr = None
1933 try:
1933 try:
1934 lock = repo.lock()
1934 lock = repo.lock()
1935 tr = repo.transaction("builddag")
1935 tr = repo.transaction("builddag")
1936
1936
1937 at = -1
1937 at = -1
1938 atbranch = 'default'
1938 atbranch = 'default'
1939 nodeids = []
1939 nodeids = []
1940 id = 0
1940 id = 0
1941 ui.progress(_('building'), id, unit=_('revisions'), total=total)
1941 ui.progress(_('building'), id, unit=_('revisions'), total=total)
1942 for type, data in dagparser.parsedag(text):
1942 for type, data in dagparser.parsedag(text):
1943 if type == 'n':
1943 if type == 'n':
1944 ui.note(('node %s\n' % str(data)))
1944 ui.note(('node %s\n' % str(data)))
1945 id, ps = data
1945 id, ps = data
1946
1946
1947 files = []
1947 files = []
1948 fctxs = {}
1948 fctxs = {}
1949
1949
1950 p2 = None
1950 p2 = None
1951 if mergeable_file:
1951 if mergeable_file:
1952 fn = "mf"
1952 fn = "mf"
1953 p1 = repo[ps[0]]
1953 p1 = repo[ps[0]]
1954 if len(ps) > 1:
1954 if len(ps) > 1:
1955 p2 = repo[ps[1]]
1955 p2 = repo[ps[1]]
1956 pa = p1.ancestor(p2)
1956 pa = p1.ancestor(p2)
1957 base, local, other = [x[fn].data() for x in (pa, p1,
1957 base, local, other = [x[fn].data() for x in (pa, p1,
1958 p2)]
1958 p2)]
1959 m3 = simplemerge.Merge3Text(base, local, other)
1959 m3 = simplemerge.Merge3Text(base, local, other)
1960 ml = [l.strip() for l in m3.merge_lines()]
1960 ml = [l.strip() for l in m3.merge_lines()]
1961 ml.append("")
1961 ml.append("")
1962 elif at > 0:
1962 elif at > 0:
1963 ml = p1[fn].data().split("\n")
1963 ml = p1[fn].data().split("\n")
1964 else:
1964 else:
1965 ml = initialmergedlines
1965 ml = initialmergedlines
1966 ml[id * linesperrev] += " r%i" % id
1966 ml[id * linesperrev] += " r%i" % id
1967 mergedtext = "\n".join(ml)
1967 mergedtext = "\n".join(ml)
1968 files.append(fn)
1968 files.append(fn)
1969 fctxs[fn] = context.memfilectx(repo, fn, mergedtext)
1969 fctxs[fn] = context.memfilectx(repo, fn, mergedtext)
1970
1970
1971 if overwritten_file:
1971 if overwritten_file:
1972 fn = "of"
1972 fn = "of"
1973 files.append(fn)
1973 files.append(fn)
1974 fctxs[fn] = context.memfilectx(repo, fn, "r%i\n" % id)
1974 fctxs[fn] = context.memfilectx(repo, fn, "r%i\n" % id)
1975
1975
1976 if new_file:
1976 if new_file:
1977 fn = "nf%i" % id
1977 fn = "nf%i" % id
1978 files.append(fn)
1978 files.append(fn)
1979 fctxs[fn] = context.memfilectx(repo, fn, "r%i\n" % id)
1979 fctxs[fn] = context.memfilectx(repo, fn, "r%i\n" % id)
1980 if len(ps) > 1:
1980 if len(ps) > 1:
1981 if not p2:
1981 if not p2:
1982 p2 = repo[ps[1]]
1982 p2 = repo[ps[1]]
1983 for fn in p2:
1983 for fn in p2:
1984 if fn.startswith("nf"):
1984 if fn.startswith("nf"):
1985 files.append(fn)
1985 files.append(fn)
1986 fctxs[fn] = p2[fn]
1986 fctxs[fn] = p2[fn]
1987
1987
1988 def fctxfn(repo, cx, path):
1988 def fctxfn(repo, cx, path):
1989 return fctxs.get(path)
1989 return fctxs.get(path)
1990
1990
1991 if len(ps) == 0 or ps[0] < 0:
1991 if len(ps) == 0 or ps[0] < 0:
1992 pars = [None, None]
1992 pars = [None, None]
1993 elif len(ps) == 1:
1993 elif len(ps) == 1:
1994 pars = [nodeids[ps[0]], None]
1994 pars = [nodeids[ps[0]], None]
1995 else:
1995 else:
1996 pars = [nodeids[p] for p in ps]
1996 pars = [nodeids[p] for p in ps]
1997 cx = context.memctx(repo, pars, "r%i" % id, files, fctxfn,
1997 cx = context.memctx(repo, pars, "r%i" % id, files, fctxfn,
1998 date=(id, 0),
1998 date=(id, 0),
1999 user="debugbuilddag",
1999 user="debugbuilddag",
2000 extra={'branch': atbranch})
2000 extra={'branch': atbranch})
2001 nodeid = repo.commitctx(cx)
2001 nodeid = repo.commitctx(cx)
2002 nodeids.append(nodeid)
2002 nodeids.append(nodeid)
2003 at = id
2003 at = id
2004 elif type == 'l':
2004 elif type == 'l':
2005 id, name = data
2005 id, name = data
2006 ui.note(('tag %s\n' % name))
2006 ui.note(('tag %s\n' % name))
2007 tags.append("%s %s\n" % (hex(repo.changelog.node(id)), name))
2007 tags.append("%s %s\n" % (hex(repo.changelog.node(id)), name))
2008 elif type == 'a':
2008 elif type == 'a':
2009 ui.note(('branch %s\n' % data))
2009 ui.note(('branch %s\n' % data))
2010 atbranch = data
2010 atbranch = data
2011 ui.progress(_('building'), id, unit=_('revisions'), total=total)
2011 ui.progress(_('building'), id, unit=_('revisions'), total=total)
2012 tr.close()
2012 tr.close()
2013
2013
2014 if tags:
2014 if tags:
2015 repo.vfs.write("localtags", "".join(tags))
2015 repo.vfs.write("localtags", "".join(tags))
2016 finally:
2016 finally:
2017 ui.progress(_('building'), None)
2017 ui.progress(_('building'), None)
2018 release(tr, lock)
2018 release(tr, lock)
2019
2019
2020 @command('debugbundle',
2020 @command('debugbundle',
2021 [('a', 'all', None, _('show all details'))],
2021 [('a', 'all', None, _('show all details'))],
2022 _('FILE'),
2022 _('FILE'),
2023 norepo=True)
2023 norepo=True)
2024 def debugbundle(ui, bundlepath, all=None, **opts):
2024 def debugbundle(ui, bundlepath, all=None, **opts):
2025 """lists the contents of a bundle"""
2025 """lists the contents of a bundle"""
2026 f = hg.openpath(ui, bundlepath)
2026 f = hg.openpath(ui, bundlepath)
2027 try:
2027 try:
2028 gen = exchange.readbundle(ui, f, bundlepath)
2028 gen = exchange.readbundle(ui, f, bundlepath)
2029 if isinstance(gen, bundle2.unbundle20):
2029 if isinstance(gen, bundle2.unbundle20):
2030 return _debugbundle2(ui, gen, all=all, **opts)
2030 return _debugbundle2(ui, gen, all=all, **opts)
2031 if all:
2031 if all:
2032 ui.write(("format: id, p1, p2, cset, delta base, len(delta)\n"))
2032 ui.write(("format: id, p1, p2, cset, delta base, len(delta)\n"))
2033
2033
2034 def showchunks(named):
2034 def showchunks(named):
2035 ui.write("\n%s\n" % named)
2035 ui.write("\n%s\n" % named)
2036 chain = None
2036 chain = None
2037 while True:
2037 while True:
2038 chunkdata = gen.deltachunk(chain)
2038 chunkdata = gen.deltachunk(chain)
2039 if not chunkdata:
2039 if not chunkdata:
2040 break
2040 break
2041 node = chunkdata['node']
2041 node = chunkdata['node']
2042 p1 = chunkdata['p1']
2042 p1 = chunkdata['p1']
2043 p2 = chunkdata['p2']
2043 p2 = chunkdata['p2']
2044 cs = chunkdata['cs']
2044 cs = chunkdata['cs']
2045 deltabase = chunkdata['deltabase']
2045 deltabase = chunkdata['deltabase']
2046 delta = chunkdata['delta']
2046 delta = chunkdata['delta']
2047 ui.write("%s %s %s %s %s %s\n" %
2047 ui.write("%s %s %s %s %s %s\n" %
2048 (hex(node), hex(p1), hex(p2),
2048 (hex(node), hex(p1), hex(p2),
2049 hex(cs), hex(deltabase), len(delta)))
2049 hex(cs), hex(deltabase), len(delta)))
2050 chain = node
2050 chain = node
2051
2051
2052 chunkdata = gen.changelogheader()
2052 chunkdata = gen.changelogheader()
2053 showchunks("changelog")
2053 showchunks("changelog")
2054 chunkdata = gen.manifestheader()
2054 chunkdata = gen.manifestheader()
2055 showchunks("manifest")
2055 showchunks("manifest")
2056 while True:
2056 while True:
2057 chunkdata = gen.filelogheader()
2057 chunkdata = gen.filelogheader()
2058 if not chunkdata:
2058 if not chunkdata:
2059 break
2059 break
2060 fname = chunkdata['filename']
2060 fname = chunkdata['filename']
2061 showchunks(fname)
2061 showchunks(fname)
2062 else:
2062 else:
2063 if isinstance(gen, bundle2.unbundle20):
2063 if isinstance(gen, bundle2.unbundle20):
2064 raise error.Abort(_('use debugbundle2 for this file'))
2064 raise error.Abort(_('use debugbundle2 for this file'))
2065 chunkdata = gen.changelogheader()
2065 chunkdata = gen.changelogheader()
2066 chain = None
2066 chain = None
2067 while True:
2067 while True:
2068 chunkdata = gen.deltachunk(chain)
2068 chunkdata = gen.deltachunk(chain)
2069 if not chunkdata:
2069 if not chunkdata:
2070 break
2070 break
2071 node = chunkdata['node']
2071 node = chunkdata['node']
2072 ui.write("%s\n" % hex(node))
2072 ui.write("%s\n" % hex(node))
2073 chain = node
2073 chain = node
2074 finally:
2074 finally:
2075 f.close()
2075 f.close()
2076
2076
2077 def _debugbundle2(ui, gen, **opts):
2077 def _debugbundle2(ui, gen, **opts):
2078 """lists the contents of a bundle2"""
2078 """lists the contents of a bundle2"""
2079 if not isinstance(gen, bundle2.unbundle20):
2079 if not isinstance(gen, bundle2.unbundle20):
2080 raise error.Abort(_('not a bundle2 file'))
2080 raise error.Abort(_('not a bundle2 file'))
2081 ui.write(('Stream params: %s\n' % repr(gen.params)))
2081 ui.write(('Stream params: %s\n' % repr(gen.params)))
2082 for part in gen.iterparts():
2082 for part in gen.iterparts():
2083 ui.write('%s -- %r\n' % (part.type, repr(part.params)))
2083 ui.write('%s -- %r\n' % (part.type, repr(part.params)))
2084 if part.type == 'changegroup':
2084 if part.type == 'changegroup':
2085 version = part.params.get('version', '01')
2085 version = part.params.get('version', '01')
2086 cg = changegroup.packermap[version][1](part, 'UN')
2086 cg = changegroup.packermap[version][1](part, 'UN')
2087 chunkdata = cg.changelogheader()
2087 chunkdata = cg.changelogheader()
2088 chain = None
2088 chain = None
2089 while True:
2089 while True:
2090 chunkdata = cg.deltachunk(chain)
2090 chunkdata = cg.deltachunk(chain)
2091 if not chunkdata:
2091 if not chunkdata:
2092 break
2092 break
2093 node = chunkdata['node']
2093 node = chunkdata['node']
2094 ui.write(" %s\n" % hex(node))
2094 ui.write(" %s\n" % hex(node))
2095 chain = node
2095 chain = node
2096
2096
2097 @command('debugcreatestreamclonebundle', [], 'FILE')
2097 @command('debugcreatestreamclonebundle', [], 'FILE')
2098 def debugcreatestreamclonebundle(ui, repo, fname):
2098 def debugcreatestreamclonebundle(ui, repo, fname):
2099 """create a stream clone bundle file
2099 """create a stream clone bundle file
2100
2100
2101 Stream bundles are special bundles that are essentially archives of
2101 Stream bundles are special bundles that are essentially archives of
2102 revlog files. They are commonly used for cloning very quickly.
2102 revlog files. They are commonly used for cloning very quickly.
2103 """
2103 """
2104 requirements, gen = streamclone.generatebundlev1(repo)
2104 requirements, gen = streamclone.generatebundlev1(repo)
2105 changegroup.writechunks(ui, gen, fname)
2105 changegroup.writechunks(ui, gen, fname)
2106
2106
2107 ui.write(_('bundle requirements: %s\n') % ', '.join(sorted(requirements)))
2107 ui.write(_('bundle requirements: %s\n') % ', '.join(sorted(requirements)))
2108
2108
2109 @command('debugapplystreamclonebundle', [], 'FILE')
2109 @command('debugapplystreamclonebundle', [], 'FILE')
2110 def debugapplystreamclonebundle(ui, repo, fname):
2110 def debugapplystreamclonebundle(ui, repo, fname):
2111 """apply a stream clone bundle file"""
2111 """apply a stream clone bundle file"""
2112 f = hg.openpath(ui, fname)
2112 f = hg.openpath(ui, fname)
2113 gen = exchange.readbundle(ui, f, fname)
2113 gen = exchange.readbundle(ui, f, fname)
2114 gen.apply(repo)
2114 gen.apply(repo)
2115
2115
2116 @command('debugcheckstate', [], '')
2116 @command('debugcheckstate', [], '')
2117 def debugcheckstate(ui, repo):
2117 def debugcheckstate(ui, repo):
2118 """validate the correctness of the current dirstate"""
2118 """validate the correctness of the current dirstate"""
2119 parent1, parent2 = repo.dirstate.parents()
2119 parent1, parent2 = repo.dirstate.parents()
2120 m1 = repo[parent1].manifest()
2120 m1 = repo[parent1].manifest()
2121 m2 = repo[parent2].manifest()
2121 m2 = repo[parent2].manifest()
2122 errors = 0
2122 errors = 0
2123 for f in repo.dirstate:
2123 for f in repo.dirstate:
2124 state = repo.dirstate[f]
2124 state = repo.dirstate[f]
2125 if state in "nr" and f not in m1:
2125 if state in "nr" and f not in m1:
2126 ui.warn(_("%s in state %s, but not in manifest1\n") % (f, state))
2126 ui.warn(_("%s in state %s, but not in manifest1\n") % (f, state))
2127 errors += 1
2127 errors += 1
2128 if state in "a" and f in m1:
2128 if state in "a" and f in m1:
2129 ui.warn(_("%s in state %s, but also in manifest1\n") % (f, state))
2129 ui.warn(_("%s in state %s, but also in manifest1\n") % (f, state))
2130 errors += 1
2130 errors += 1
2131 if state in "m" and f not in m1 and f not in m2:
2131 if state in "m" and f not in m1 and f not in m2:
2132 ui.warn(_("%s in state %s, but not in either manifest\n") %
2132 ui.warn(_("%s in state %s, but not in either manifest\n") %
2133 (f, state))
2133 (f, state))
2134 errors += 1
2134 errors += 1
2135 for f in m1:
2135 for f in m1:
2136 state = repo.dirstate[f]
2136 state = repo.dirstate[f]
2137 if state not in "nrm":
2137 if state not in "nrm":
2138 ui.warn(_("%s in manifest1, but listed as state %s") % (f, state))
2138 ui.warn(_("%s in manifest1, but listed as state %s") % (f, state))
2139 errors += 1
2139 errors += 1
2140 if errors:
2140 if errors:
2141 error = _(".hg/dirstate inconsistent with current parent's manifest")
2141 error = _(".hg/dirstate inconsistent with current parent's manifest")
2142 raise error.Abort(error)
2142 raise error.Abort(error)
2143
2143
2144 @command('debugcommands', [], _('[COMMAND]'), norepo=True)
2144 @command('debugcommands', [], _('[COMMAND]'), norepo=True)
2145 def debugcommands(ui, cmd='', *args):
2145 def debugcommands(ui, cmd='', *args):
2146 """list all available commands and options"""
2146 """list all available commands and options"""
2147 for cmd, vals in sorted(table.iteritems()):
2147 for cmd, vals in sorted(table.iteritems()):
2148 cmd = cmd.split('|')[0].strip('^')
2148 cmd = cmd.split('|')[0].strip('^')
2149 opts = ', '.join([i[1] for i in vals[1]])
2149 opts = ', '.join([i[1] for i in vals[1]])
2150 ui.write('%s: %s\n' % (cmd, opts))
2150 ui.write('%s: %s\n' % (cmd, opts))
2151
2151
2152 @command('debugcomplete',
2152 @command('debugcomplete',
2153 [('o', 'options', None, _('show the command options'))],
2153 [('o', 'options', None, _('show the command options'))],
2154 _('[-o] CMD'),
2154 _('[-o] CMD'),
2155 norepo=True)
2155 norepo=True)
2156 def debugcomplete(ui, cmd='', **opts):
2156 def debugcomplete(ui, cmd='', **opts):
2157 """returns the completion list associated with the given command"""
2157 """returns the completion list associated with the given command"""
2158
2158
2159 if opts.get('options'):
2159 if opts.get('options'):
2160 options = []
2160 options = []
2161 otables = [globalopts]
2161 otables = [globalopts]
2162 if cmd:
2162 if cmd:
2163 aliases, entry = cmdutil.findcmd(cmd, table, False)
2163 aliases, entry = cmdutil.findcmd(cmd, table, False)
2164 otables.append(entry[1])
2164 otables.append(entry[1])
2165 for t in otables:
2165 for t in otables:
2166 for o in t:
2166 for o in t:
2167 if "(DEPRECATED)" in o[3]:
2167 if "(DEPRECATED)" in o[3]:
2168 continue
2168 continue
2169 if o[0]:
2169 if o[0]:
2170 options.append('-%s' % o[0])
2170 options.append('-%s' % o[0])
2171 options.append('--%s' % o[1])
2171 options.append('--%s' % o[1])
2172 ui.write("%s\n" % "\n".join(options))
2172 ui.write("%s\n" % "\n".join(options))
2173 return
2173 return
2174
2174
2175 cmdlist, unused_allcmds = cmdutil.findpossible(cmd, table)
2175 cmdlist, unused_allcmds = cmdutil.findpossible(cmd, table)
2176 if ui.verbose:
2176 if ui.verbose:
2177 cmdlist = [' '.join(c[0]) for c in cmdlist.values()]
2177 cmdlist = [' '.join(c[0]) for c in cmdlist.values()]
2178 ui.write("%s\n" % "\n".join(sorted(cmdlist)))
2178 ui.write("%s\n" % "\n".join(sorted(cmdlist)))
2179
2179
2180 @command('debugdag',
2180 @command('debugdag',
2181 [('t', 'tags', None, _('use tags as labels')),
2181 [('t', 'tags', None, _('use tags as labels')),
2182 ('b', 'branches', None, _('annotate with branch names')),
2182 ('b', 'branches', None, _('annotate with branch names')),
2183 ('', 'dots', None, _('use dots for runs')),
2183 ('', 'dots', None, _('use dots for runs')),
2184 ('s', 'spaces', None, _('separate elements by spaces'))],
2184 ('s', 'spaces', None, _('separate elements by spaces'))],
2185 _('[OPTION]... [FILE [REV]...]'),
2185 _('[OPTION]... [FILE [REV]...]'),
2186 optionalrepo=True)
2186 optionalrepo=True)
2187 def debugdag(ui, repo, file_=None, *revs, **opts):
2187 def debugdag(ui, repo, file_=None, *revs, **opts):
2188 """format the changelog or an index DAG as a concise textual description
2188 """format the changelog or an index DAG as a concise textual description
2189
2189
2190 If you pass a revlog index, the revlog's DAG is emitted. If you list
2190 If you pass a revlog index, the revlog's DAG is emitted. If you list
2191 revision numbers, they get labeled in the output as rN.
2191 revision numbers, they get labeled in the output as rN.
2192
2192
2193 Otherwise, the changelog DAG of the current repo is emitted.
2193 Otherwise, the changelog DAG of the current repo is emitted.
2194 """
2194 """
2195 spaces = opts.get('spaces')
2195 spaces = opts.get('spaces')
2196 dots = opts.get('dots')
2196 dots = opts.get('dots')
2197 if file_:
2197 if file_:
2198 rlog = revlog.revlog(scmutil.opener(os.getcwd(), audit=False), file_)
2198 rlog = revlog.revlog(scmutil.opener(os.getcwd(), audit=False), file_)
2199 revs = set((int(r) for r in revs))
2199 revs = set((int(r) for r in revs))
2200 def events():
2200 def events():
2201 for r in rlog:
2201 for r in rlog:
2202 yield 'n', (r, list(p for p in rlog.parentrevs(r)
2202 yield 'n', (r, list(p for p in rlog.parentrevs(r)
2203 if p != -1))
2203 if p != -1))
2204 if r in revs:
2204 if r in revs:
2205 yield 'l', (r, "r%i" % r)
2205 yield 'l', (r, "r%i" % r)
2206 elif repo:
2206 elif repo:
2207 cl = repo.changelog
2207 cl = repo.changelog
2208 tags = opts.get('tags')
2208 tags = opts.get('tags')
2209 branches = opts.get('branches')
2209 branches = opts.get('branches')
2210 if tags:
2210 if tags:
2211 labels = {}
2211 labels = {}
2212 for l, n in repo.tags().items():
2212 for l, n in repo.tags().items():
2213 labels.setdefault(cl.rev(n), []).append(l)
2213 labels.setdefault(cl.rev(n), []).append(l)
2214 def events():
2214 def events():
2215 b = "default"
2215 b = "default"
2216 for r in cl:
2216 for r in cl:
2217 if branches:
2217 if branches:
2218 newb = cl.read(cl.node(r))[5]['branch']
2218 newb = cl.read(cl.node(r))[5]['branch']
2219 if newb != b:
2219 if newb != b:
2220 yield 'a', newb
2220 yield 'a', newb
2221 b = newb
2221 b = newb
2222 yield 'n', (r, list(p for p in cl.parentrevs(r)
2222 yield 'n', (r, list(p for p in cl.parentrevs(r)
2223 if p != -1))
2223 if p != -1))
2224 if tags:
2224 if tags:
2225 ls = labels.get(r)
2225 ls = labels.get(r)
2226 if ls:
2226 if ls:
2227 for l in ls:
2227 for l in ls:
2228 yield 'l', (r, l)
2228 yield 'l', (r, l)
2229 else:
2229 else:
2230 raise error.Abort(_('need repo for changelog dag'))
2230 raise error.Abort(_('need repo for changelog dag'))
2231
2231
2232 for line in dagparser.dagtextlines(events(),
2232 for line in dagparser.dagtextlines(events(),
2233 addspaces=spaces,
2233 addspaces=spaces,
2234 wraplabels=True,
2234 wraplabels=True,
2235 wrapannotations=True,
2235 wrapannotations=True,
2236 wrapnonlinear=dots,
2236 wrapnonlinear=dots,
2237 usedots=dots,
2237 usedots=dots,
2238 maxlinewidth=70):
2238 maxlinewidth=70):
2239 ui.write(line)
2239 ui.write(line)
2240 ui.write("\n")
2240 ui.write("\n")
2241
2241
2242 @command('debugdata', debugrevlogopts, _('-c|-m|FILE REV'))
2242 @command('debugdata', debugrevlogopts, _('-c|-m|FILE REV'))
2243 def debugdata(ui, repo, file_, rev=None, **opts):
2243 def debugdata(ui, repo, file_, rev=None, **opts):
2244 """dump the contents of a data file revision"""
2244 """dump the contents of a data file revision"""
2245 if opts.get('changelog') or opts.get('manifest'):
2245 if opts.get('changelog') or opts.get('manifest'):
2246 file_, rev = None, file_
2246 file_, rev = None, file_
2247 elif rev is None:
2247 elif rev is None:
2248 raise error.CommandError('debugdata', _('invalid arguments'))
2248 raise error.CommandError('debugdata', _('invalid arguments'))
2249 r = cmdutil.openrevlog(repo, 'debugdata', file_, opts)
2249 r = cmdutil.openrevlog(repo, 'debugdata', file_, opts)
2250 try:
2250 try:
2251 ui.write(r.revision(r.lookup(rev)))
2251 ui.write(r.revision(r.lookup(rev)))
2252 except KeyError:
2252 except KeyError:
2253 raise error.Abort(_('invalid revision identifier %s') % rev)
2253 raise error.Abort(_('invalid revision identifier %s') % rev)
2254
2254
2255 @command('debugdate',
2255 @command('debugdate',
2256 [('e', 'extended', None, _('try extended date formats'))],
2256 [('e', 'extended', None, _('try extended date formats'))],
2257 _('[-e] DATE [RANGE]'),
2257 _('[-e] DATE [RANGE]'),
2258 norepo=True, optionalrepo=True)
2258 norepo=True, optionalrepo=True)
2259 def debugdate(ui, date, range=None, **opts):
2259 def debugdate(ui, date, range=None, **opts):
2260 """parse and display a date"""
2260 """parse and display a date"""
2261 if opts["extended"]:
2261 if opts["extended"]:
2262 d = util.parsedate(date, util.extendeddateformats)
2262 d = util.parsedate(date, util.extendeddateformats)
2263 else:
2263 else:
2264 d = util.parsedate(date)
2264 d = util.parsedate(date)
2265 ui.write(("internal: %s %s\n") % d)
2265 ui.write(("internal: %s %s\n") % d)
2266 ui.write(("standard: %s\n") % util.datestr(d))
2266 ui.write(("standard: %s\n") % util.datestr(d))
2267 if range:
2267 if range:
2268 m = util.matchdate(range)
2268 m = util.matchdate(range)
2269 ui.write(("match: %s\n") % m(d[0]))
2269 ui.write(("match: %s\n") % m(d[0]))
2270
2270
2271 @command('debugdiscovery',
2271 @command('debugdiscovery',
2272 [('', 'old', None, _('use old-style discovery')),
2272 [('', 'old', None, _('use old-style discovery')),
2273 ('', 'nonheads', None,
2273 ('', 'nonheads', None,
2274 _('use old-style discovery with non-heads included')),
2274 _('use old-style discovery with non-heads included')),
2275 ] + remoteopts,
2275 ] + remoteopts,
2276 _('[-l REV] [-r REV] [-b BRANCH]... [OTHER]'))
2276 _('[-l REV] [-r REV] [-b BRANCH]... [OTHER]'))
2277 def debugdiscovery(ui, repo, remoteurl="default", **opts):
2277 def debugdiscovery(ui, repo, remoteurl="default", **opts):
2278 """runs the changeset discovery protocol in isolation"""
2278 """runs the changeset discovery protocol in isolation"""
2279 remoteurl, branches = hg.parseurl(ui.expandpath(remoteurl),
2279 remoteurl, branches = hg.parseurl(ui.expandpath(remoteurl),
2280 opts.get('branch'))
2280 opts.get('branch'))
2281 remote = hg.peer(repo, opts, remoteurl)
2281 remote = hg.peer(repo, opts, remoteurl)
2282 ui.status(_('comparing with %s\n') % util.hidepassword(remoteurl))
2282 ui.status(_('comparing with %s\n') % util.hidepassword(remoteurl))
2283
2283
2284 # make sure tests are repeatable
2284 # make sure tests are repeatable
2285 random.seed(12323)
2285 random.seed(12323)
2286
2286
2287 def doit(localheads, remoteheads, remote=remote):
2287 def doit(localheads, remoteheads, remote=remote):
2288 if opts.get('old'):
2288 if opts.get('old'):
2289 if localheads:
2289 if localheads:
2290 raise error.Abort('cannot use localheads with old style '
2290 raise error.Abort('cannot use localheads with old style '
2291 'discovery')
2291 'discovery')
2292 if not util.safehasattr(remote, 'branches'):
2292 if not util.safehasattr(remote, 'branches'):
2293 # enable in-client legacy support
2293 # enable in-client legacy support
2294 remote = localrepo.locallegacypeer(remote.local())
2294 remote = localrepo.locallegacypeer(remote.local())
2295 common, _in, hds = treediscovery.findcommonincoming(repo, remote,
2295 common, _in, hds = treediscovery.findcommonincoming(repo, remote,
2296 force=True)
2296 force=True)
2297 common = set(common)
2297 common = set(common)
2298 if not opts.get('nonheads'):
2298 if not opts.get('nonheads'):
2299 ui.write(("unpruned common: %s\n") %
2299 ui.write(("unpruned common: %s\n") %
2300 " ".join(sorted(short(n) for n in common)))
2300 " ".join(sorted(short(n) for n in common)))
2301 dag = dagutil.revlogdag(repo.changelog)
2301 dag = dagutil.revlogdag(repo.changelog)
2302 all = dag.ancestorset(dag.internalizeall(common))
2302 all = dag.ancestorset(dag.internalizeall(common))
2303 common = dag.externalizeall(dag.headsetofconnecteds(all))
2303 common = dag.externalizeall(dag.headsetofconnecteds(all))
2304 else:
2304 else:
2305 common, any, hds = setdiscovery.findcommonheads(ui, repo, remote)
2305 common, any, hds = setdiscovery.findcommonheads(ui, repo, remote)
2306 common = set(common)
2306 common = set(common)
2307 rheads = set(hds)
2307 rheads = set(hds)
2308 lheads = set(repo.heads())
2308 lheads = set(repo.heads())
2309 ui.write(("common heads: %s\n") %
2309 ui.write(("common heads: %s\n") %
2310 " ".join(sorted(short(n) for n in common)))
2310 " ".join(sorted(short(n) for n in common)))
2311 if lheads <= common:
2311 if lheads <= common:
2312 ui.write(("local is subset\n"))
2312 ui.write(("local is subset\n"))
2313 elif rheads <= common:
2313 elif rheads <= common:
2314 ui.write(("remote is subset\n"))
2314 ui.write(("remote is subset\n"))
2315
2315
2316 serverlogs = opts.get('serverlog')
2316 serverlogs = opts.get('serverlog')
2317 if serverlogs:
2317 if serverlogs:
2318 for filename in serverlogs:
2318 for filename in serverlogs:
2319 logfile = open(filename, 'r')
2319 logfile = open(filename, 'r')
2320 try:
2320 try:
2321 line = logfile.readline()
2321 line = logfile.readline()
2322 while line:
2322 while line:
2323 parts = line.strip().split(';')
2323 parts = line.strip().split(';')
2324 op = parts[1]
2324 op = parts[1]
2325 if op == 'cg':
2325 if op == 'cg':
2326 pass
2326 pass
2327 elif op == 'cgss':
2327 elif op == 'cgss':
2328 doit(parts[2].split(' '), parts[3].split(' '))
2328 doit(parts[2].split(' '), parts[3].split(' '))
2329 elif op == 'unb':
2329 elif op == 'unb':
2330 doit(parts[3].split(' '), parts[2].split(' '))
2330 doit(parts[3].split(' '), parts[2].split(' '))
2331 line = logfile.readline()
2331 line = logfile.readline()
2332 finally:
2332 finally:
2333 logfile.close()
2333 logfile.close()
2334
2334
2335 else:
2335 else:
2336 remoterevs, _checkout = hg.addbranchrevs(repo, remote, branches,
2336 remoterevs, _checkout = hg.addbranchrevs(repo, remote, branches,
2337 opts.get('remote_head'))
2337 opts.get('remote_head'))
2338 localrevs = opts.get('local_head')
2338 localrevs = opts.get('local_head')
2339 doit(localrevs, remoterevs)
2339 doit(localrevs, remoterevs)
2340
2340
2341 @command('debugextensions', formatteropts, [], norepo=True)
2341 @command('debugextensions', formatteropts, [], norepo=True)
2342 def debugextensions(ui, **opts):
2342 def debugextensions(ui, **opts):
2343 '''show information about active extensions'''
2343 '''show information about active extensions'''
2344 exts = extensions.extensions(ui)
2344 exts = extensions.extensions(ui)
2345 fm = ui.formatter('debugextensions', opts)
2345 fm = ui.formatter('debugextensions', opts)
2346 for extname, extmod in sorted(exts, key=operator.itemgetter(0)):
2346 for extname, extmod in sorted(exts, key=operator.itemgetter(0)):
2347 extsource = extmod.__file__
2347 extsource = extmod.__file__
2348 exttestedwith = getattr(extmod, 'testedwith', None)
2348 exttestedwith = getattr(extmod, 'testedwith', None)
2349 if exttestedwith is not None:
2349 if exttestedwith is not None:
2350 exttestedwith = exttestedwith.split()
2350 exttestedwith = exttestedwith.split()
2351 extbuglink = getattr(extmod, 'buglink', None)
2351 extbuglink = getattr(extmod, 'buglink', None)
2352
2352
2353 fm.startitem()
2353 fm.startitem()
2354
2354
2355 if ui.quiet or ui.verbose:
2355 if ui.quiet or ui.verbose:
2356 fm.write('name', '%s\n', extname)
2356 fm.write('name', '%s\n', extname)
2357 else:
2357 else:
2358 fm.write('name', '%s', extname)
2358 fm.write('name', '%s', extname)
2359 if not exttestedwith:
2359 if not exttestedwith:
2360 fm.plain(_(' (untested!)\n'))
2360 fm.plain(_(' (untested!)\n'))
2361 else:
2361 else:
2362 if exttestedwith == ['internal'] or \
2362 if exttestedwith == ['internal'] or \
2363 util.version() in exttestedwith:
2363 util.version() in exttestedwith:
2364 fm.plain('\n')
2364 fm.plain('\n')
2365 else:
2365 else:
2366 lasttestedversion = exttestedwith[-1]
2366 lasttestedversion = exttestedwith[-1]
2367 fm.plain(' (%s!)\n' % lasttestedversion)
2367 fm.plain(' (%s!)\n' % lasttestedversion)
2368
2368
2369 fm.condwrite(ui.verbose and extsource, 'source',
2369 fm.condwrite(ui.verbose and extsource, 'source',
2370 _(' location: %s\n'), extsource or "")
2370 _(' location: %s\n'), extsource or "")
2371
2371
2372 fm.condwrite(ui.verbose and exttestedwith, 'testedwith',
2372 fm.condwrite(ui.verbose and exttestedwith, 'testedwith',
2373 _(' tested with: %s\n'), ' '.join(exttestedwith or []))
2373 _(' tested with: %s\n'), ' '.join(exttestedwith or []))
2374
2374
2375 fm.condwrite(ui.verbose and extbuglink, 'buglink',
2375 fm.condwrite(ui.verbose and extbuglink, 'buglink',
2376 _(' bug reporting: %s\n'), extbuglink or "")
2376 _(' bug reporting: %s\n'), extbuglink or "")
2377
2377
2378 fm.end()
2378 fm.end()
2379
2379
2380 @command('debugfileset',
2380 @command('debugfileset',
2381 [('r', 'rev', '', _('apply the filespec on this revision'), _('REV'))],
2381 [('r', 'rev', '', _('apply the filespec on this revision'), _('REV'))],
2382 _('[-r REV] FILESPEC'))
2382 _('[-r REV] FILESPEC'))
2383 def debugfileset(ui, repo, expr, **opts):
2383 def debugfileset(ui, repo, expr, **opts):
2384 '''parse and apply a fileset specification'''
2384 '''parse and apply a fileset specification'''
2385 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
2385 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
2386 if ui.verbose:
2386 if ui.verbose:
2387 tree = fileset.parse(expr)
2387 tree = fileset.parse(expr)
2388 ui.note(fileset.prettyformat(tree), "\n")
2388 ui.note(fileset.prettyformat(tree), "\n")
2389
2389
2390 for f in ctx.getfileset(expr):
2390 for f in ctx.getfileset(expr):
2391 ui.write("%s\n" % f)
2391 ui.write("%s\n" % f)
2392
2392
2393 @command('debugfsinfo', [], _('[PATH]'), norepo=True)
2393 @command('debugfsinfo', [], _('[PATH]'), norepo=True)
2394 def debugfsinfo(ui, path="."):
2394 def debugfsinfo(ui, path="."):
2395 """show information detected about current filesystem"""
2395 """show information detected about current filesystem"""
2396 util.writefile('.debugfsinfo', '')
2396 util.writefile('.debugfsinfo', '')
2397 ui.write(('exec: %s\n') % (util.checkexec(path) and 'yes' or 'no'))
2397 ui.write(('exec: %s\n') % (util.checkexec(path) and 'yes' or 'no'))
2398 ui.write(('symlink: %s\n') % (util.checklink(path) and 'yes' or 'no'))
2398 ui.write(('symlink: %s\n') % (util.checklink(path) and 'yes' or 'no'))
2399 ui.write(('hardlink: %s\n') % (util.checknlink(path) and 'yes' or 'no'))
2399 ui.write(('hardlink: %s\n') % (util.checknlink(path) and 'yes' or 'no'))
2400 ui.write(('case-sensitive: %s\n') % (util.checkcase('.debugfsinfo')
2400 ui.write(('case-sensitive: %s\n') % (util.checkcase('.debugfsinfo')
2401 and 'yes' or 'no'))
2401 and 'yes' or 'no'))
2402 os.unlink('.debugfsinfo')
2402 os.unlink('.debugfsinfo')
2403
2403
2404 @command('debuggetbundle',
2404 @command('debuggetbundle',
2405 [('H', 'head', [], _('id of head node'), _('ID')),
2405 [('H', 'head', [], _('id of head node'), _('ID')),
2406 ('C', 'common', [], _('id of common node'), _('ID')),
2406 ('C', 'common', [], _('id of common node'), _('ID')),
2407 ('t', 'type', 'bzip2', _('bundle compression type to use'), _('TYPE'))],
2407 ('t', 'type', 'bzip2', _('bundle compression type to use'), _('TYPE'))],
2408 _('REPO FILE [-H|-C ID]...'),
2408 _('REPO FILE [-H|-C ID]...'),
2409 norepo=True)
2409 norepo=True)
2410 def debuggetbundle(ui, repopath, bundlepath, head=None, common=None, **opts):
2410 def debuggetbundle(ui, repopath, bundlepath, head=None, common=None, **opts):
2411 """retrieves a bundle from a repo
2411 """retrieves a bundle from a repo
2412
2412
2413 Every ID must be a full-length hex node id string. Saves the bundle to the
2413 Every ID must be a full-length hex node id string. Saves the bundle to the
2414 given file.
2414 given file.
2415 """
2415 """
2416 repo = hg.peer(ui, opts, repopath)
2416 repo = hg.peer(ui, opts, repopath)
2417 if not repo.capable('getbundle'):
2417 if not repo.capable('getbundle'):
2418 raise error.Abort("getbundle() not supported by target repository")
2418 raise error.Abort("getbundle() not supported by target repository")
2419 args = {}
2419 args = {}
2420 if common:
2420 if common:
2421 args['common'] = [bin(s) for s in common]
2421 args['common'] = [bin(s) for s in common]
2422 if head:
2422 if head:
2423 args['heads'] = [bin(s) for s in head]
2423 args['heads'] = [bin(s) for s in head]
2424 # TODO: get desired bundlecaps from command line.
2424 # TODO: get desired bundlecaps from command line.
2425 args['bundlecaps'] = None
2425 args['bundlecaps'] = None
2426 bundle = repo.getbundle('debug', **args)
2426 bundle = repo.getbundle('debug', **args)
2427
2427
2428 bundletype = opts.get('type', 'bzip2').lower()
2428 bundletype = opts.get('type', 'bzip2').lower()
2429 btypes = {'none': 'HG10UN',
2429 btypes = {'none': 'HG10UN',
2430 'bzip2': 'HG10BZ',
2430 'bzip2': 'HG10BZ',
2431 'gzip': 'HG10GZ',
2431 'gzip': 'HG10GZ',
2432 'bundle2': 'HG20'}
2432 'bundle2': 'HG20'}
2433 bundletype = btypes.get(bundletype)
2433 bundletype = btypes.get(bundletype)
2434 if bundletype not in changegroup.bundletypes:
2434 if bundletype not in changegroup.bundletypes:
2435 raise error.Abort(_('unknown bundle type specified with --type'))
2435 raise error.Abort(_('unknown bundle type specified with --type'))
2436 changegroup.writebundle(ui, bundle, bundlepath, bundletype)
2436 changegroup.writebundle(ui, bundle, bundlepath, bundletype)
2437
2437
2438 @command('debugignore', [], '')
2438 @command('debugignore', [], '[FILE]')
2439 def debugignore(ui, repo, *values, **opts):
2439 def debugignore(ui, repo, *files, **opts):
2440 """display the combined ignore pattern"""
2440 """display the combined ignore pattern and information about ignored files
2441
2442 With no argument display the combined ignore pattern.
2443
2444 Given space separated file names, shows if the given file is ignored.
2445 """
2441 ignore = repo.dirstate._ignore
2446 ignore = repo.dirstate._ignore
2442 includepat = getattr(ignore, 'includepat', None)
2447 if not files:
2443 if includepat is not None:
2448 # Show all the patterns
2444 ui.write("%s\n" % includepat)
2449 includepat = getattr(ignore, 'includepat', None)
2450 if includepat is not None:
2451 ui.write("%s\n" % includepat)
2452 else:
2453 raise error.Abort(_("no ignore patterns found"))
2445 else:
2454 else:
2446 raise error.Abort(_("no ignore patterns found"))
2455 for f in files:
2456 ignored = None
2457 if f != '.':
2458 if ignore(f):
2459 ignored = f
2460 else:
2461 for p in util.finddirs(f):
2462 if ignore(p):
2463 ignored = p
2464 break
2465 if ignored:
2466 if ignored == f:
2467 ui.write("%s is ignored\n" % f)
2468 else:
2469 ui.write("%s is ignored because of containing folder %s\n"
2470 % (f, ignored))
2471 else:
2472 ui.write("%s is not ignored\n" % f)
2447
2473
2448 @command('debugindex', debugrevlogopts +
2474 @command('debugindex', debugrevlogopts +
2449 [('f', 'format', 0, _('revlog format'), _('FORMAT'))],
2475 [('f', 'format', 0, _('revlog format'), _('FORMAT'))],
2450 _('[-f FORMAT] -c|-m|FILE'),
2476 _('[-f FORMAT] -c|-m|FILE'),
2451 optionalrepo=True)
2477 optionalrepo=True)
2452 def debugindex(ui, repo, file_=None, **opts):
2478 def debugindex(ui, repo, file_=None, **opts):
2453 """dump the contents of an index file"""
2479 """dump the contents of an index file"""
2454 r = cmdutil.openrevlog(repo, 'debugindex', file_, opts)
2480 r = cmdutil.openrevlog(repo, 'debugindex', file_, opts)
2455 format = opts.get('format', 0)
2481 format = opts.get('format', 0)
2456 if format not in (0, 1):
2482 if format not in (0, 1):
2457 raise error.Abort(_("unknown format %d") % format)
2483 raise error.Abort(_("unknown format %d") % format)
2458
2484
2459 generaldelta = r.version & revlog.REVLOGGENERALDELTA
2485 generaldelta = r.version & revlog.REVLOGGENERALDELTA
2460 if generaldelta:
2486 if generaldelta:
2461 basehdr = ' delta'
2487 basehdr = ' delta'
2462 else:
2488 else:
2463 basehdr = ' base'
2489 basehdr = ' base'
2464
2490
2465 if ui.debugflag:
2491 if ui.debugflag:
2466 shortfn = hex
2492 shortfn = hex
2467 else:
2493 else:
2468 shortfn = short
2494 shortfn = short
2469
2495
2470 # There might not be anything in r, so have a sane default
2496 # There might not be anything in r, so have a sane default
2471 idlen = 12
2497 idlen = 12
2472 for i in r:
2498 for i in r:
2473 idlen = len(shortfn(r.node(i)))
2499 idlen = len(shortfn(r.node(i)))
2474 break
2500 break
2475
2501
2476 if format == 0:
2502 if format == 0:
2477 ui.write(" rev offset length " + basehdr + " linkrev"
2503 ui.write(" rev offset length " + basehdr + " linkrev"
2478 " %s %s p2\n" % ("nodeid".ljust(idlen), "p1".ljust(idlen)))
2504 " %s %s p2\n" % ("nodeid".ljust(idlen), "p1".ljust(idlen)))
2479 elif format == 1:
2505 elif format == 1:
2480 ui.write(" rev flag offset length"
2506 ui.write(" rev flag offset length"
2481 " size " + basehdr + " link p1 p2"
2507 " size " + basehdr + " link p1 p2"
2482 " %s\n" % "nodeid".rjust(idlen))
2508 " %s\n" % "nodeid".rjust(idlen))
2483
2509
2484 for i in r:
2510 for i in r:
2485 node = r.node(i)
2511 node = r.node(i)
2486 if generaldelta:
2512 if generaldelta:
2487 base = r.deltaparent(i)
2513 base = r.deltaparent(i)
2488 else:
2514 else:
2489 base = r.chainbase(i)
2515 base = r.chainbase(i)
2490 if format == 0:
2516 if format == 0:
2491 try:
2517 try:
2492 pp = r.parents(node)
2518 pp = r.parents(node)
2493 except Exception:
2519 except Exception:
2494 pp = [nullid, nullid]
2520 pp = [nullid, nullid]
2495 ui.write("% 6d % 9d % 7d % 6d % 7d %s %s %s\n" % (
2521 ui.write("% 6d % 9d % 7d % 6d % 7d %s %s %s\n" % (
2496 i, r.start(i), r.length(i), base, r.linkrev(i),
2522 i, r.start(i), r.length(i), base, r.linkrev(i),
2497 shortfn(node), shortfn(pp[0]), shortfn(pp[1])))
2523 shortfn(node), shortfn(pp[0]), shortfn(pp[1])))
2498 elif format == 1:
2524 elif format == 1:
2499 pr = r.parentrevs(i)
2525 pr = r.parentrevs(i)
2500 ui.write("% 6d %04x % 8d % 8d % 8d % 6d % 6d % 6d % 6d %s\n" % (
2526 ui.write("% 6d %04x % 8d % 8d % 8d % 6d % 6d % 6d % 6d %s\n" % (
2501 i, r.flags(i), r.start(i), r.length(i), r.rawsize(i),
2527 i, r.flags(i), r.start(i), r.length(i), r.rawsize(i),
2502 base, r.linkrev(i), pr[0], pr[1], shortfn(node)))
2528 base, r.linkrev(i), pr[0], pr[1], shortfn(node)))
2503
2529
2504 @command('debugindexdot', debugrevlogopts,
2530 @command('debugindexdot', debugrevlogopts,
2505 _('-c|-m|FILE'), optionalrepo=True)
2531 _('-c|-m|FILE'), optionalrepo=True)
2506 def debugindexdot(ui, repo, file_=None, **opts):
2532 def debugindexdot(ui, repo, file_=None, **opts):
2507 """dump an index DAG as a graphviz dot file"""
2533 """dump an index DAG as a graphviz dot file"""
2508 r = cmdutil.openrevlog(repo, 'debugindexdot', file_, opts)
2534 r = cmdutil.openrevlog(repo, 'debugindexdot', file_, opts)
2509 ui.write(("digraph G {\n"))
2535 ui.write(("digraph G {\n"))
2510 for i in r:
2536 for i in r:
2511 node = r.node(i)
2537 node = r.node(i)
2512 pp = r.parents(node)
2538 pp = r.parents(node)
2513 ui.write("\t%d -> %d\n" % (r.rev(pp[0]), i))
2539 ui.write("\t%d -> %d\n" % (r.rev(pp[0]), i))
2514 if pp[1] != nullid:
2540 if pp[1] != nullid:
2515 ui.write("\t%d -> %d\n" % (r.rev(pp[1]), i))
2541 ui.write("\t%d -> %d\n" % (r.rev(pp[1]), i))
2516 ui.write("}\n")
2542 ui.write("}\n")
2517
2543
2518 @command('debugdeltachain',
2544 @command('debugdeltachain',
2519 debugrevlogopts + formatteropts,
2545 debugrevlogopts + formatteropts,
2520 _('-c|-m|FILE'),
2546 _('-c|-m|FILE'),
2521 optionalrepo=True)
2547 optionalrepo=True)
2522 def debugdeltachain(ui, repo, file_=None, **opts):
2548 def debugdeltachain(ui, repo, file_=None, **opts):
2523 """dump information about delta chains in a revlog
2549 """dump information about delta chains in a revlog
2524
2550
2525 Output can be templatized. Available template keywords are:
2551 Output can be templatized. Available template keywords are:
2526
2552
2527 rev revision number
2553 rev revision number
2528 chainid delta chain identifier (numbered by unique base)
2554 chainid delta chain identifier (numbered by unique base)
2529 chainlen delta chain length to this revision
2555 chainlen delta chain length to this revision
2530 prevrev previous revision in delta chain
2556 prevrev previous revision in delta chain
2531 deltatype role of delta / how it was computed
2557 deltatype role of delta / how it was computed
2532 compsize compressed size of revision
2558 compsize compressed size of revision
2533 uncompsize uncompressed size of revision
2559 uncompsize uncompressed size of revision
2534 chainsize total size of compressed revisions in chain
2560 chainsize total size of compressed revisions in chain
2535 chainratio total chain size divided by uncompressed revision size
2561 chainratio total chain size divided by uncompressed revision size
2536 (new delta chains typically start at ratio 2.00)
2562 (new delta chains typically start at ratio 2.00)
2537 lindist linear distance from base revision in delta chain to end
2563 lindist linear distance from base revision in delta chain to end
2538 of this revision
2564 of this revision
2539 extradist total size of revisions not part of this delta chain from
2565 extradist total size of revisions not part of this delta chain from
2540 base of delta chain to end of this revision; a measurement
2566 base of delta chain to end of this revision; a measurement
2541 of how much extra data we need to read/seek across to read
2567 of how much extra data we need to read/seek across to read
2542 the delta chain for this revision
2568 the delta chain for this revision
2543 extraratio extradist divided by chainsize; another representation of
2569 extraratio extradist divided by chainsize; another representation of
2544 how much unrelated data is needed to load this delta chain
2570 how much unrelated data is needed to load this delta chain
2545 """
2571 """
2546 r = cmdutil.openrevlog(repo, 'debugdeltachain', file_, opts)
2572 r = cmdutil.openrevlog(repo, 'debugdeltachain', file_, opts)
2547 index = r.index
2573 index = r.index
2548 generaldelta = r.version & revlog.REVLOGGENERALDELTA
2574 generaldelta = r.version & revlog.REVLOGGENERALDELTA
2549
2575
2550 def revinfo(rev):
2576 def revinfo(rev):
2551 e = index[rev]
2577 e = index[rev]
2552 compsize = e[1]
2578 compsize = e[1]
2553 uncompsize = e[2]
2579 uncompsize = e[2]
2554 chainsize = 0
2580 chainsize = 0
2555
2581
2556 if generaldelta:
2582 if generaldelta:
2557 if e[3] == e[5]:
2583 if e[3] == e[5]:
2558 deltatype = 'p1'
2584 deltatype = 'p1'
2559 elif e[3] == e[6]:
2585 elif e[3] == e[6]:
2560 deltatype = 'p2'
2586 deltatype = 'p2'
2561 elif e[3] == rev - 1:
2587 elif e[3] == rev - 1:
2562 deltatype = 'prev'
2588 deltatype = 'prev'
2563 elif e[3] == rev:
2589 elif e[3] == rev:
2564 deltatype = 'base'
2590 deltatype = 'base'
2565 else:
2591 else:
2566 deltatype = 'other'
2592 deltatype = 'other'
2567 else:
2593 else:
2568 if e[3] == rev:
2594 if e[3] == rev:
2569 deltatype = 'base'
2595 deltatype = 'base'
2570 else:
2596 else:
2571 deltatype = 'prev'
2597 deltatype = 'prev'
2572
2598
2573 chain = r._deltachain(rev)[0]
2599 chain = r._deltachain(rev)[0]
2574 for iterrev in chain:
2600 for iterrev in chain:
2575 e = index[iterrev]
2601 e = index[iterrev]
2576 chainsize += e[1]
2602 chainsize += e[1]
2577
2603
2578 return compsize, uncompsize, deltatype, chain, chainsize
2604 return compsize, uncompsize, deltatype, chain, chainsize
2579
2605
2580 fm = ui.formatter('debugdeltachain', opts)
2606 fm = ui.formatter('debugdeltachain', opts)
2581
2607
2582 fm.plain(' rev chain# chainlen prev delta '
2608 fm.plain(' rev chain# chainlen prev delta '
2583 'size rawsize chainsize ratio lindist extradist '
2609 'size rawsize chainsize ratio lindist extradist '
2584 'extraratio\n')
2610 'extraratio\n')
2585
2611
2586 chainbases = {}
2612 chainbases = {}
2587 for rev in r:
2613 for rev in r:
2588 comp, uncomp, deltatype, chain, chainsize = revinfo(rev)
2614 comp, uncomp, deltatype, chain, chainsize = revinfo(rev)
2589 chainbase = chain[0]
2615 chainbase = chain[0]
2590 chainid = chainbases.setdefault(chainbase, len(chainbases) + 1)
2616 chainid = chainbases.setdefault(chainbase, len(chainbases) + 1)
2591 basestart = r.start(chainbase)
2617 basestart = r.start(chainbase)
2592 revstart = r.start(rev)
2618 revstart = r.start(rev)
2593 lineardist = revstart + comp - basestart
2619 lineardist = revstart + comp - basestart
2594 extradist = lineardist - chainsize
2620 extradist = lineardist - chainsize
2595 try:
2621 try:
2596 prevrev = chain[-2]
2622 prevrev = chain[-2]
2597 except IndexError:
2623 except IndexError:
2598 prevrev = -1
2624 prevrev = -1
2599
2625
2600 chainratio = float(chainsize) / float(uncomp)
2626 chainratio = float(chainsize) / float(uncomp)
2601 extraratio = float(extradist) / float(chainsize)
2627 extraratio = float(extradist) / float(chainsize)
2602
2628
2603 fm.startitem()
2629 fm.startitem()
2604 fm.write('rev chainid chainlen prevrev deltatype compsize '
2630 fm.write('rev chainid chainlen prevrev deltatype compsize '
2605 'uncompsize chainsize chainratio lindist extradist '
2631 'uncompsize chainsize chainratio lindist extradist '
2606 'extraratio',
2632 'extraratio',
2607 '%7d %7d %8d %8d %7s %10d %10d %10d %9.5f %9d %9d %10.5f\n',
2633 '%7d %7d %8d %8d %7s %10d %10d %10d %9.5f %9d %9d %10.5f\n',
2608 rev, chainid, len(chain), prevrev, deltatype, comp,
2634 rev, chainid, len(chain), prevrev, deltatype, comp,
2609 uncomp, chainsize, chainratio, lineardist, extradist,
2635 uncomp, chainsize, chainratio, lineardist, extradist,
2610 extraratio,
2636 extraratio,
2611 rev=rev, chainid=chainid, chainlen=len(chain),
2637 rev=rev, chainid=chainid, chainlen=len(chain),
2612 prevrev=prevrev, deltatype=deltatype, compsize=comp,
2638 prevrev=prevrev, deltatype=deltatype, compsize=comp,
2613 uncompsize=uncomp, chainsize=chainsize,
2639 uncompsize=uncomp, chainsize=chainsize,
2614 chainratio=chainratio, lindist=lineardist,
2640 chainratio=chainratio, lindist=lineardist,
2615 extradist=extradist, extraratio=extraratio)
2641 extradist=extradist, extraratio=extraratio)
2616
2642
2617 fm.end()
2643 fm.end()
2618
2644
2619 @command('debuginstall', [], '', norepo=True)
2645 @command('debuginstall', [], '', norepo=True)
2620 def debuginstall(ui):
2646 def debuginstall(ui):
2621 '''test Mercurial installation
2647 '''test Mercurial installation
2622
2648
2623 Returns 0 on success.
2649 Returns 0 on success.
2624 '''
2650 '''
2625
2651
2626 def writetemp(contents):
2652 def writetemp(contents):
2627 (fd, name) = tempfile.mkstemp(prefix="hg-debuginstall-")
2653 (fd, name) = tempfile.mkstemp(prefix="hg-debuginstall-")
2628 f = os.fdopen(fd, "wb")
2654 f = os.fdopen(fd, "wb")
2629 f.write(contents)
2655 f.write(contents)
2630 f.close()
2656 f.close()
2631 return name
2657 return name
2632
2658
2633 problems = 0
2659 problems = 0
2634
2660
2635 # encoding
2661 # encoding
2636 ui.status(_("checking encoding (%s)...\n") % encoding.encoding)
2662 ui.status(_("checking encoding (%s)...\n") % encoding.encoding)
2637 try:
2663 try:
2638 encoding.fromlocal("test")
2664 encoding.fromlocal("test")
2639 except error.Abort as inst:
2665 except error.Abort as inst:
2640 ui.write(" %s\n" % inst)
2666 ui.write(" %s\n" % inst)
2641 ui.write(_(" (check that your locale is properly set)\n"))
2667 ui.write(_(" (check that your locale is properly set)\n"))
2642 problems += 1
2668 problems += 1
2643
2669
2644 # Python
2670 # Python
2645 ui.status(_("checking Python executable (%s)\n") % sys.executable)
2671 ui.status(_("checking Python executable (%s)\n") % sys.executable)
2646 ui.status(_("checking Python version (%s)\n")
2672 ui.status(_("checking Python version (%s)\n")
2647 % ("%s.%s.%s" % sys.version_info[:3]))
2673 % ("%s.%s.%s" % sys.version_info[:3]))
2648 ui.status(_("checking Python lib (%s)...\n")
2674 ui.status(_("checking Python lib (%s)...\n")
2649 % os.path.dirname(os.__file__))
2675 % os.path.dirname(os.__file__))
2650
2676
2651 # compiled modules
2677 # compiled modules
2652 ui.status(_("checking installed modules (%s)...\n")
2678 ui.status(_("checking installed modules (%s)...\n")
2653 % os.path.dirname(__file__))
2679 % os.path.dirname(__file__))
2654 try:
2680 try:
2655 import bdiff, mpatch, base85, osutil
2681 import bdiff, mpatch, base85, osutil
2656 dir(bdiff), dir(mpatch), dir(base85), dir(osutil) # quiet pyflakes
2682 dir(bdiff), dir(mpatch), dir(base85), dir(osutil) # quiet pyflakes
2657 except Exception as inst:
2683 except Exception as inst:
2658 ui.write(" %s\n" % inst)
2684 ui.write(" %s\n" % inst)
2659 ui.write(_(" One or more extensions could not be found"))
2685 ui.write(_(" One or more extensions could not be found"))
2660 ui.write(_(" (check that you compiled the extensions)\n"))
2686 ui.write(_(" (check that you compiled the extensions)\n"))
2661 problems += 1
2687 problems += 1
2662
2688
2663 # templates
2689 # templates
2664 import templater
2690 import templater
2665 p = templater.templatepaths()
2691 p = templater.templatepaths()
2666 ui.status(_("checking templates (%s)...\n") % ' '.join(p))
2692 ui.status(_("checking templates (%s)...\n") % ' '.join(p))
2667 if p:
2693 if p:
2668 m = templater.templatepath("map-cmdline.default")
2694 m = templater.templatepath("map-cmdline.default")
2669 if m:
2695 if m:
2670 # template found, check if it is working
2696 # template found, check if it is working
2671 try:
2697 try:
2672 templater.templater(m)
2698 templater.templater(m)
2673 except Exception as inst:
2699 except Exception as inst:
2674 ui.write(" %s\n" % inst)
2700 ui.write(" %s\n" % inst)
2675 p = None
2701 p = None
2676 else:
2702 else:
2677 ui.write(_(" template 'default' not found\n"))
2703 ui.write(_(" template 'default' not found\n"))
2678 p = None
2704 p = None
2679 else:
2705 else:
2680 ui.write(_(" no template directories found\n"))
2706 ui.write(_(" no template directories found\n"))
2681 if not p:
2707 if not p:
2682 ui.write(_(" (templates seem to have been installed incorrectly)\n"))
2708 ui.write(_(" (templates seem to have been installed incorrectly)\n"))
2683 problems += 1
2709 problems += 1
2684
2710
2685 # editor
2711 # editor
2686 ui.status(_("checking commit editor...\n"))
2712 ui.status(_("checking commit editor...\n"))
2687 editor = ui.geteditor()
2713 editor = ui.geteditor()
2688 editor = util.expandpath(editor)
2714 editor = util.expandpath(editor)
2689 cmdpath = util.findexe(shlex.split(editor)[0])
2715 cmdpath = util.findexe(shlex.split(editor)[0])
2690 if not cmdpath:
2716 if not cmdpath:
2691 if editor == 'vi':
2717 if editor == 'vi':
2692 ui.write(_(" No commit editor set and can't find vi in PATH\n"))
2718 ui.write(_(" No commit editor set and can't find vi in PATH\n"))
2693 ui.write(_(" (specify a commit editor in your configuration"
2719 ui.write(_(" (specify a commit editor in your configuration"
2694 " file)\n"))
2720 " file)\n"))
2695 else:
2721 else:
2696 ui.write(_(" Can't find editor '%s' in PATH\n") % editor)
2722 ui.write(_(" Can't find editor '%s' in PATH\n") % editor)
2697 ui.write(_(" (specify a commit editor in your configuration"
2723 ui.write(_(" (specify a commit editor in your configuration"
2698 " file)\n"))
2724 " file)\n"))
2699 problems += 1
2725 problems += 1
2700
2726
2701 # check username
2727 # check username
2702 ui.status(_("checking username...\n"))
2728 ui.status(_("checking username...\n"))
2703 try:
2729 try:
2704 ui.username()
2730 ui.username()
2705 except error.Abort as e:
2731 except error.Abort as e:
2706 ui.write(" %s\n" % e)
2732 ui.write(" %s\n" % e)
2707 ui.write(_(" (specify a username in your configuration file)\n"))
2733 ui.write(_(" (specify a username in your configuration file)\n"))
2708 problems += 1
2734 problems += 1
2709
2735
2710 if not problems:
2736 if not problems:
2711 ui.status(_("no problems detected\n"))
2737 ui.status(_("no problems detected\n"))
2712 else:
2738 else:
2713 ui.write(_("%s problems detected,"
2739 ui.write(_("%s problems detected,"
2714 " please check your install!\n") % problems)
2740 " please check your install!\n") % problems)
2715
2741
2716 return problems
2742 return problems
2717
2743
2718 @command('debugknown', [], _('REPO ID...'), norepo=True)
2744 @command('debugknown', [], _('REPO ID...'), norepo=True)
2719 def debugknown(ui, repopath, *ids, **opts):
2745 def debugknown(ui, repopath, *ids, **opts):
2720 """test whether node ids are known to a repo
2746 """test whether node ids are known to a repo
2721
2747
2722 Every ID must be a full-length hex node id string. Returns a list of 0s
2748 Every ID must be a full-length hex node id string. Returns a list of 0s
2723 and 1s indicating unknown/known.
2749 and 1s indicating unknown/known.
2724 """
2750 """
2725 repo = hg.peer(ui, opts, repopath)
2751 repo = hg.peer(ui, opts, repopath)
2726 if not repo.capable('known'):
2752 if not repo.capable('known'):
2727 raise error.Abort("known() not supported by target repository")
2753 raise error.Abort("known() not supported by target repository")
2728 flags = repo.known([bin(s) for s in ids])
2754 flags = repo.known([bin(s) for s in ids])
2729 ui.write("%s\n" % ("".join([f and "1" or "0" for f in flags])))
2755 ui.write("%s\n" % ("".join([f and "1" or "0" for f in flags])))
2730
2756
2731 @command('debuglabelcomplete', [], _('LABEL...'))
2757 @command('debuglabelcomplete', [], _('LABEL...'))
2732 def debuglabelcomplete(ui, repo, *args):
2758 def debuglabelcomplete(ui, repo, *args):
2733 '''backwards compatibility with old bash completion scripts (DEPRECATED)'''
2759 '''backwards compatibility with old bash completion scripts (DEPRECATED)'''
2734 debugnamecomplete(ui, repo, *args)
2760 debugnamecomplete(ui, repo, *args)
2735
2761
2736 @command('debugmergestate', [], '')
2762 @command('debugmergestate', [], '')
2737 def debugmergestate(ui, repo, *args):
2763 def debugmergestate(ui, repo, *args):
2738 """print merge state
2764 """print merge state
2739
2765
2740 Use --verbose to print out information about whether v1 or v2 merge state
2766 Use --verbose to print out information about whether v1 or v2 merge state
2741 was chosen."""
2767 was chosen."""
2742 def _hashornull(h):
2768 def _hashornull(h):
2743 if h == nullhex:
2769 if h == nullhex:
2744 return 'null'
2770 return 'null'
2745 else:
2771 else:
2746 return h
2772 return h
2747
2773
2748 def printrecords(version):
2774 def printrecords(version):
2749 ui.write(('* version %s records\n') % version)
2775 ui.write(('* version %s records\n') % version)
2750 if version == 1:
2776 if version == 1:
2751 records = v1records
2777 records = v1records
2752 else:
2778 else:
2753 records = v2records
2779 records = v2records
2754
2780
2755 for rtype, record in records:
2781 for rtype, record in records:
2756 # pretty print some record types
2782 # pretty print some record types
2757 if rtype == 'L':
2783 if rtype == 'L':
2758 ui.write(('local: %s\n') % record)
2784 ui.write(('local: %s\n') % record)
2759 elif rtype == 'O':
2785 elif rtype == 'O':
2760 ui.write(('other: %s\n') % record)
2786 ui.write(('other: %s\n') % record)
2761 elif rtype == 'm':
2787 elif rtype == 'm':
2762 driver, mdstate = record.split('\0', 1)
2788 driver, mdstate = record.split('\0', 1)
2763 ui.write(('merge driver: %s (state "%s")\n')
2789 ui.write(('merge driver: %s (state "%s")\n')
2764 % (driver, mdstate))
2790 % (driver, mdstate))
2765 elif rtype in 'FDC':
2791 elif rtype in 'FDC':
2766 r = record.split('\0')
2792 r = record.split('\0')
2767 f, state, hash, lfile, afile, anode, ofile = r[0:7]
2793 f, state, hash, lfile, afile, anode, ofile = r[0:7]
2768 if version == 1:
2794 if version == 1:
2769 onode = 'not stored in v1 format'
2795 onode = 'not stored in v1 format'
2770 flags = r[7]
2796 flags = r[7]
2771 else:
2797 else:
2772 onode, flags = r[7:9]
2798 onode, flags = r[7:9]
2773 ui.write(('file: %s (record type "%s", state "%s", hash %s)\n')
2799 ui.write(('file: %s (record type "%s", state "%s", hash %s)\n')
2774 % (f, rtype, state, _hashornull(hash)))
2800 % (f, rtype, state, _hashornull(hash)))
2775 ui.write((' local path: %s (flags "%s")\n') % (lfile, flags))
2801 ui.write((' local path: %s (flags "%s")\n') % (lfile, flags))
2776 ui.write((' ancestor path: %s (node %s)\n')
2802 ui.write((' ancestor path: %s (node %s)\n')
2777 % (afile, _hashornull(anode)))
2803 % (afile, _hashornull(anode)))
2778 ui.write((' other path: %s (node %s)\n')
2804 ui.write((' other path: %s (node %s)\n')
2779 % (ofile, _hashornull(onode)))
2805 % (ofile, _hashornull(onode)))
2780 else:
2806 else:
2781 ui.write(('unrecognized entry: %s\t%s\n')
2807 ui.write(('unrecognized entry: %s\t%s\n')
2782 % (rtype, record.replace('\0', '\t')))
2808 % (rtype, record.replace('\0', '\t')))
2783
2809
2784 # Avoid mergestate.read() since it may raise an exception for unsupported
2810 # Avoid mergestate.read() since it may raise an exception for unsupported
2785 # merge state records. We shouldn't be doing this, but this is OK since this
2811 # merge state records. We shouldn't be doing this, but this is OK since this
2786 # command is pretty low-level.
2812 # command is pretty low-level.
2787 ms = mergemod.mergestate(repo)
2813 ms = mergemod.mergestate(repo)
2788
2814
2789 # sort so that reasonable information is on top
2815 # sort so that reasonable information is on top
2790 v1records = ms._readrecordsv1()
2816 v1records = ms._readrecordsv1()
2791 v2records = ms._readrecordsv2()
2817 v2records = ms._readrecordsv2()
2792 order = 'LOm'
2818 order = 'LOm'
2793 def key(r):
2819 def key(r):
2794 idx = order.find(r[0])
2820 idx = order.find(r[0])
2795 if idx == -1:
2821 if idx == -1:
2796 return (1, r[1])
2822 return (1, r[1])
2797 else:
2823 else:
2798 return (0, idx)
2824 return (0, idx)
2799 v1records.sort(key=key)
2825 v1records.sort(key=key)
2800 v2records.sort(key=key)
2826 v2records.sort(key=key)
2801
2827
2802 if not v1records and not v2records:
2828 if not v1records and not v2records:
2803 ui.write(('no merge state found\n'))
2829 ui.write(('no merge state found\n'))
2804 elif not v2records:
2830 elif not v2records:
2805 ui.note(('no version 2 merge state\n'))
2831 ui.note(('no version 2 merge state\n'))
2806 printrecords(1)
2832 printrecords(1)
2807 elif ms._v1v2match(v1records, v2records):
2833 elif ms._v1v2match(v1records, v2records):
2808 ui.note(('v1 and v2 states match: using v2\n'))
2834 ui.note(('v1 and v2 states match: using v2\n'))
2809 printrecords(2)
2835 printrecords(2)
2810 else:
2836 else:
2811 ui.note(('v1 and v2 states mismatch: using v1\n'))
2837 ui.note(('v1 and v2 states mismatch: using v1\n'))
2812 printrecords(1)
2838 printrecords(1)
2813 if ui.verbose:
2839 if ui.verbose:
2814 printrecords(2)
2840 printrecords(2)
2815
2841
2816 @command('debugnamecomplete', [], _('NAME...'))
2842 @command('debugnamecomplete', [], _('NAME...'))
2817 def debugnamecomplete(ui, repo, *args):
2843 def debugnamecomplete(ui, repo, *args):
2818 '''complete "names" - tags, open branch names, bookmark names'''
2844 '''complete "names" - tags, open branch names, bookmark names'''
2819
2845
2820 names = set()
2846 names = set()
2821 # since we previously only listed open branches, we will handle that
2847 # since we previously only listed open branches, we will handle that
2822 # specially (after this for loop)
2848 # specially (after this for loop)
2823 for name, ns in repo.names.iteritems():
2849 for name, ns in repo.names.iteritems():
2824 if name != 'branches':
2850 if name != 'branches':
2825 names.update(ns.listnames(repo))
2851 names.update(ns.listnames(repo))
2826 names.update(tag for (tag, heads, tip, closed)
2852 names.update(tag for (tag, heads, tip, closed)
2827 in repo.branchmap().iterbranches() if not closed)
2853 in repo.branchmap().iterbranches() if not closed)
2828 completions = set()
2854 completions = set()
2829 if not args:
2855 if not args:
2830 args = ['']
2856 args = ['']
2831 for a in args:
2857 for a in args:
2832 completions.update(n for n in names if n.startswith(a))
2858 completions.update(n for n in names if n.startswith(a))
2833 ui.write('\n'.join(sorted(completions)))
2859 ui.write('\n'.join(sorted(completions)))
2834 ui.write('\n')
2860 ui.write('\n')
2835
2861
2836 @command('debuglocks',
2862 @command('debuglocks',
2837 [('L', 'force-lock', None, _('free the store lock (DANGEROUS)')),
2863 [('L', 'force-lock', None, _('free the store lock (DANGEROUS)')),
2838 ('W', 'force-wlock', None,
2864 ('W', 'force-wlock', None,
2839 _('free the working state lock (DANGEROUS)'))],
2865 _('free the working state lock (DANGEROUS)'))],
2840 _('[OPTION]...'))
2866 _('[OPTION]...'))
2841 def debuglocks(ui, repo, **opts):
2867 def debuglocks(ui, repo, **opts):
2842 """show or modify state of locks
2868 """show or modify state of locks
2843
2869
2844 By default, this command will show which locks are held. This
2870 By default, this command will show which locks are held. This
2845 includes the user and process holding the lock, the amount of time
2871 includes the user and process holding the lock, the amount of time
2846 the lock has been held, and the machine name where the process is
2872 the lock has been held, and the machine name where the process is
2847 running if it's not local.
2873 running if it's not local.
2848
2874
2849 Locks protect the integrity of Mercurial's data, so should be
2875 Locks protect the integrity of Mercurial's data, so should be
2850 treated with care. System crashes or other interruptions may cause
2876 treated with care. System crashes or other interruptions may cause
2851 locks to not be properly released, though Mercurial will usually
2877 locks to not be properly released, though Mercurial will usually
2852 detect and remove such stale locks automatically.
2878 detect and remove such stale locks automatically.
2853
2879
2854 However, detecting stale locks may not always be possible (for
2880 However, detecting stale locks may not always be possible (for
2855 instance, on a shared filesystem). Removing locks may also be
2881 instance, on a shared filesystem). Removing locks may also be
2856 blocked by filesystem permissions.
2882 blocked by filesystem permissions.
2857
2883
2858 Returns 0 if no locks are held.
2884 Returns 0 if no locks are held.
2859
2885
2860 """
2886 """
2861
2887
2862 if opts.get('force_lock'):
2888 if opts.get('force_lock'):
2863 repo.svfs.unlink('lock')
2889 repo.svfs.unlink('lock')
2864 if opts.get('force_wlock'):
2890 if opts.get('force_wlock'):
2865 repo.vfs.unlink('wlock')
2891 repo.vfs.unlink('wlock')
2866 if opts.get('force_lock') or opts.get('force_lock'):
2892 if opts.get('force_lock') or opts.get('force_lock'):
2867 return 0
2893 return 0
2868
2894
2869 now = time.time()
2895 now = time.time()
2870 held = 0
2896 held = 0
2871
2897
2872 def report(vfs, name, method):
2898 def report(vfs, name, method):
2873 # this causes stale locks to get reaped for more accurate reporting
2899 # this causes stale locks to get reaped for more accurate reporting
2874 try:
2900 try:
2875 l = method(False)
2901 l = method(False)
2876 except error.LockHeld:
2902 except error.LockHeld:
2877 l = None
2903 l = None
2878
2904
2879 if l:
2905 if l:
2880 l.release()
2906 l.release()
2881 else:
2907 else:
2882 try:
2908 try:
2883 stat = vfs.lstat(name)
2909 stat = vfs.lstat(name)
2884 age = now - stat.st_mtime
2910 age = now - stat.st_mtime
2885 user = util.username(stat.st_uid)
2911 user = util.username(stat.st_uid)
2886 locker = vfs.readlock(name)
2912 locker = vfs.readlock(name)
2887 if ":" in locker:
2913 if ":" in locker:
2888 host, pid = locker.split(':')
2914 host, pid = locker.split(':')
2889 if host == socket.gethostname():
2915 if host == socket.gethostname():
2890 locker = 'user %s, process %s' % (user, pid)
2916 locker = 'user %s, process %s' % (user, pid)
2891 else:
2917 else:
2892 locker = 'user %s, process %s, host %s' \
2918 locker = 'user %s, process %s, host %s' \
2893 % (user, pid, host)
2919 % (user, pid, host)
2894 ui.write("%-6s %s (%ds)\n" % (name + ":", locker, age))
2920 ui.write("%-6s %s (%ds)\n" % (name + ":", locker, age))
2895 return 1
2921 return 1
2896 except OSError as e:
2922 except OSError as e:
2897 if e.errno != errno.ENOENT:
2923 if e.errno != errno.ENOENT:
2898 raise
2924 raise
2899
2925
2900 ui.write("%-6s free\n" % (name + ":"))
2926 ui.write("%-6s free\n" % (name + ":"))
2901 return 0
2927 return 0
2902
2928
2903 held += report(repo.svfs, "lock", repo.lock)
2929 held += report(repo.svfs, "lock", repo.lock)
2904 held += report(repo.vfs, "wlock", repo.wlock)
2930 held += report(repo.vfs, "wlock", repo.wlock)
2905
2931
2906 return held
2932 return held
2907
2933
2908 @command('debugobsolete',
2934 @command('debugobsolete',
2909 [('', 'flags', 0, _('markers flag')),
2935 [('', 'flags', 0, _('markers flag')),
2910 ('', 'record-parents', False,
2936 ('', 'record-parents', False,
2911 _('record parent information for the precursor')),
2937 _('record parent information for the precursor')),
2912 ('r', 'rev', [], _('display markers relevant to REV')),
2938 ('r', 'rev', [], _('display markers relevant to REV')),
2913 ] + commitopts2,
2939 ] + commitopts2,
2914 _('[OBSOLETED [REPLACEMENT ...]]'))
2940 _('[OBSOLETED [REPLACEMENT ...]]'))
2915 def debugobsolete(ui, repo, precursor=None, *successors, **opts):
2941 def debugobsolete(ui, repo, precursor=None, *successors, **opts):
2916 """create arbitrary obsolete marker
2942 """create arbitrary obsolete marker
2917
2943
2918 With no arguments, displays the list of obsolescence markers."""
2944 With no arguments, displays the list of obsolescence markers."""
2919
2945
2920 def parsenodeid(s):
2946 def parsenodeid(s):
2921 try:
2947 try:
2922 # We do not use revsingle/revrange functions here to accept
2948 # We do not use revsingle/revrange functions here to accept
2923 # arbitrary node identifiers, possibly not present in the
2949 # arbitrary node identifiers, possibly not present in the
2924 # local repository.
2950 # local repository.
2925 n = bin(s)
2951 n = bin(s)
2926 if len(n) != len(nullid):
2952 if len(n) != len(nullid):
2927 raise TypeError()
2953 raise TypeError()
2928 return n
2954 return n
2929 except TypeError:
2955 except TypeError:
2930 raise error.Abort('changeset references must be full hexadecimal '
2956 raise error.Abort('changeset references must be full hexadecimal '
2931 'node identifiers')
2957 'node identifiers')
2932
2958
2933 if precursor is not None:
2959 if precursor is not None:
2934 if opts['rev']:
2960 if opts['rev']:
2935 raise error.Abort('cannot select revision when creating marker')
2961 raise error.Abort('cannot select revision when creating marker')
2936 metadata = {}
2962 metadata = {}
2937 metadata['user'] = opts['user'] or ui.username()
2963 metadata['user'] = opts['user'] or ui.username()
2938 succs = tuple(parsenodeid(succ) for succ in successors)
2964 succs = tuple(parsenodeid(succ) for succ in successors)
2939 l = repo.lock()
2965 l = repo.lock()
2940 try:
2966 try:
2941 tr = repo.transaction('debugobsolete')
2967 tr = repo.transaction('debugobsolete')
2942 try:
2968 try:
2943 date = opts.get('date')
2969 date = opts.get('date')
2944 if date:
2970 if date:
2945 date = util.parsedate(date)
2971 date = util.parsedate(date)
2946 else:
2972 else:
2947 date = None
2973 date = None
2948 prec = parsenodeid(precursor)
2974 prec = parsenodeid(precursor)
2949 parents = None
2975 parents = None
2950 if opts['record_parents']:
2976 if opts['record_parents']:
2951 if prec not in repo.unfiltered():
2977 if prec not in repo.unfiltered():
2952 raise error.Abort('cannot used --record-parents on '
2978 raise error.Abort('cannot used --record-parents on '
2953 'unknown changesets')
2979 'unknown changesets')
2954 parents = repo.unfiltered()[prec].parents()
2980 parents = repo.unfiltered()[prec].parents()
2955 parents = tuple(p.node() for p in parents)
2981 parents = tuple(p.node() for p in parents)
2956 repo.obsstore.create(tr, prec, succs, opts['flags'],
2982 repo.obsstore.create(tr, prec, succs, opts['flags'],
2957 parents=parents, date=date,
2983 parents=parents, date=date,
2958 metadata=metadata)
2984 metadata=metadata)
2959 tr.close()
2985 tr.close()
2960 except ValueError as exc:
2986 except ValueError as exc:
2961 raise error.Abort(_('bad obsmarker input: %s') % exc)
2987 raise error.Abort(_('bad obsmarker input: %s') % exc)
2962 finally:
2988 finally:
2963 tr.release()
2989 tr.release()
2964 finally:
2990 finally:
2965 l.release()
2991 l.release()
2966 else:
2992 else:
2967 if opts['rev']:
2993 if opts['rev']:
2968 revs = scmutil.revrange(repo, opts['rev'])
2994 revs = scmutil.revrange(repo, opts['rev'])
2969 nodes = [repo[r].node() for r in revs]
2995 nodes = [repo[r].node() for r in revs]
2970 markers = list(obsolete.getmarkers(repo, nodes=nodes))
2996 markers = list(obsolete.getmarkers(repo, nodes=nodes))
2971 markers.sort(key=lambda x: x._data)
2997 markers.sort(key=lambda x: x._data)
2972 else:
2998 else:
2973 markers = obsolete.getmarkers(repo)
2999 markers = obsolete.getmarkers(repo)
2974
3000
2975 for m in markers:
3001 for m in markers:
2976 cmdutil.showmarker(ui, m)
3002 cmdutil.showmarker(ui, m)
2977
3003
2978 @command('debugpathcomplete',
3004 @command('debugpathcomplete',
2979 [('f', 'full', None, _('complete an entire path')),
3005 [('f', 'full', None, _('complete an entire path')),
2980 ('n', 'normal', None, _('show only normal files')),
3006 ('n', 'normal', None, _('show only normal files')),
2981 ('a', 'added', None, _('show only added files')),
3007 ('a', 'added', None, _('show only added files')),
2982 ('r', 'removed', None, _('show only removed files'))],
3008 ('r', 'removed', None, _('show only removed files'))],
2983 _('FILESPEC...'))
3009 _('FILESPEC...'))
2984 def debugpathcomplete(ui, repo, *specs, **opts):
3010 def debugpathcomplete(ui, repo, *specs, **opts):
2985 '''complete part or all of a tracked path
3011 '''complete part or all of a tracked path
2986
3012
2987 This command supports shells that offer path name completion. It
3013 This command supports shells that offer path name completion. It
2988 currently completes only files already known to the dirstate.
3014 currently completes only files already known to the dirstate.
2989
3015
2990 Completion extends only to the next path segment unless
3016 Completion extends only to the next path segment unless
2991 --full is specified, in which case entire paths are used.'''
3017 --full is specified, in which case entire paths are used.'''
2992
3018
2993 def complete(path, acceptable):
3019 def complete(path, acceptable):
2994 dirstate = repo.dirstate
3020 dirstate = repo.dirstate
2995 spec = os.path.normpath(os.path.join(os.getcwd(), path))
3021 spec = os.path.normpath(os.path.join(os.getcwd(), path))
2996 rootdir = repo.root + os.sep
3022 rootdir = repo.root + os.sep
2997 if spec != repo.root and not spec.startswith(rootdir):
3023 if spec != repo.root and not spec.startswith(rootdir):
2998 return [], []
3024 return [], []
2999 if os.path.isdir(spec):
3025 if os.path.isdir(spec):
3000 spec += '/'
3026 spec += '/'
3001 spec = spec[len(rootdir):]
3027 spec = spec[len(rootdir):]
3002 fixpaths = os.sep != '/'
3028 fixpaths = os.sep != '/'
3003 if fixpaths:
3029 if fixpaths:
3004 spec = spec.replace(os.sep, '/')
3030 spec = spec.replace(os.sep, '/')
3005 speclen = len(spec)
3031 speclen = len(spec)
3006 fullpaths = opts['full']
3032 fullpaths = opts['full']
3007 files, dirs = set(), set()
3033 files, dirs = set(), set()
3008 adddir, addfile = dirs.add, files.add
3034 adddir, addfile = dirs.add, files.add
3009 for f, st in dirstate.iteritems():
3035 for f, st in dirstate.iteritems():
3010 if f.startswith(spec) and st[0] in acceptable:
3036 if f.startswith(spec) and st[0] in acceptable:
3011 if fixpaths:
3037 if fixpaths:
3012 f = f.replace('/', os.sep)
3038 f = f.replace('/', os.sep)
3013 if fullpaths:
3039 if fullpaths:
3014 addfile(f)
3040 addfile(f)
3015 continue
3041 continue
3016 s = f.find(os.sep, speclen)
3042 s = f.find(os.sep, speclen)
3017 if s >= 0:
3043 if s >= 0:
3018 adddir(f[:s])
3044 adddir(f[:s])
3019 else:
3045 else:
3020 addfile(f)
3046 addfile(f)
3021 return files, dirs
3047 return files, dirs
3022
3048
3023 acceptable = ''
3049 acceptable = ''
3024 if opts['normal']:
3050 if opts['normal']:
3025 acceptable += 'nm'
3051 acceptable += 'nm'
3026 if opts['added']:
3052 if opts['added']:
3027 acceptable += 'a'
3053 acceptable += 'a'
3028 if opts['removed']:
3054 if opts['removed']:
3029 acceptable += 'r'
3055 acceptable += 'r'
3030 cwd = repo.getcwd()
3056 cwd = repo.getcwd()
3031 if not specs:
3057 if not specs:
3032 specs = ['.']
3058 specs = ['.']
3033
3059
3034 files, dirs = set(), set()
3060 files, dirs = set(), set()
3035 for spec in specs:
3061 for spec in specs:
3036 f, d = complete(spec, acceptable or 'nmar')
3062 f, d = complete(spec, acceptable or 'nmar')
3037 files.update(f)
3063 files.update(f)
3038 dirs.update(d)
3064 dirs.update(d)
3039 files.update(dirs)
3065 files.update(dirs)
3040 ui.write('\n'.join(repo.pathto(p, cwd) for p in sorted(files)))
3066 ui.write('\n'.join(repo.pathto(p, cwd) for p in sorted(files)))
3041 ui.write('\n')
3067 ui.write('\n')
3042
3068
3043 @command('debugpushkey', [], _('REPO NAMESPACE [KEY OLD NEW]'), norepo=True)
3069 @command('debugpushkey', [], _('REPO NAMESPACE [KEY OLD NEW]'), norepo=True)
3044 def debugpushkey(ui, repopath, namespace, *keyinfo, **opts):
3070 def debugpushkey(ui, repopath, namespace, *keyinfo, **opts):
3045 '''access the pushkey key/value protocol
3071 '''access the pushkey key/value protocol
3046
3072
3047 With two args, list the keys in the given namespace.
3073 With two args, list the keys in the given namespace.
3048
3074
3049 With five args, set a key to new if it currently is set to old.
3075 With five args, set a key to new if it currently is set to old.
3050 Reports success or failure.
3076 Reports success or failure.
3051 '''
3077 '''
3052
3078
3053 target = hg.peer(ui, {}, repopath)
3079 target = hg.peer(ui, {}, repopath)
3054 if keyinfo:
3080 if keyinfo:
3055 key, old, new = keyinfo
3081 key, old, new = keyinfo
3056 r = target.pushkey(namespace, key, old, new)
3082 r = target.pushkey(namespace, key, old, new)
3057 ui.status(str(r) + '\n')
3083 ui.status(str(r) + '\n')
3058 return not r
3084 return not r
3059 else:
3085 else:
3060 for k, v in sorted(target.listkeys(namespace).iteritems()):
3086 for k, v in sorted(target.listkeys(namespace).iteritems()):
3061 ui.write("%s\t%s\n" % (k.encode('string-escape'),
3087 ui.write("%s\t%s\n" % (k.encode('string-escape'),
3062 v.encode('string-escape')))
3088 v.encode('string-escape')))
3063
3089
3064 @command('debugpvec', [], _('A B'))
3090 @command('debugpvec', [], _('A B'))
3065 def debugpvec(ui, repo, a, b=None):
3091 def debugpvec(ui, repo, a, b=None):
3066 ca = scmutil.revsingle(repo, a)
3092 ca = scmutil.revsingle(repo, a)
3067 cb = scmutil.revsingle(repo, b)
3093 cb = scmutil.revsingle(repo, b)
3068 pa = pvec.ctxpvec(ca)
3094 pa = pvec.ctxpvec(ca)
3069 pb = pvec.ctxpvec(cb)
3095 pb = pvec.ctxpvec(cb)
3070 if pa == pb:
3096 if pa == pb:
3071 rel = "="
3097 rel = "="
3072 elif pa > pb:
3098 elif pa > pb:
3073 rel = ">"
3099 rel = ">"
3074 elif pa < pb:
3100 elif pa < pb:
3075 rel = "<"
3101 rel = "<"
3076 elif pa | pb:
3102 elif pa | pb:
3077 rel = "|"
3103 rel = "|"
3078 ui.write(_("a: %s\n") % pa)
3104 ui.write(_("a: %s\n") % pa)
3079 ui.write(_("b: %s\n") % pb)
3105 ui.write(_("b: %s\n") % pb)
3080 ui.write(_("depth(a): %d depth(b): %d\n") % (pa._depth, pb._depth))
3106 ui.write(_("depth(a): %d depth(b): %d\n") % (pa._depth, pb._depth))
3081 ui.write(_("delta: %d hdist: %d distance: %d relation: %s\n") %
3107 ui.write(_("delta: %d hdist: %d distance: %d relation: %s\n") %
3082 (abs(pa._depth - pb._depth), pvec._hamming(pa._vec, pb._vec),
3108 (abs(pa._depth - pb._depth), pvec._hamming(pa._vec, pb._vec),
3083 pa.distance(pb), rel))
3109 pa.distance(pb), rel))
3084
3110
3085 @command('debugrebuilddirstate|debugrebuildstate',
3111 @command('debugrebuilddirstate|debugrebuildstate',
3086 [('r', 'rev', '', _('revision to rebuild to'), _('REV')),
3112 [('r', 'rev', '', _('revision to rebuild to'), _('REV')),
3087 ('', 'minimal', None, _('only rebuild files that are inconsistent with '
3113 ('', 'minimal', None, _('only rebuild files that are inconsistent with '
3088 'the working copy parent')),
3114 'the working copy parent')),
3089 ],
3115 ],
3090 _('[-r REV]'))
3116 _('[-r REV]'))
3091 def debugrebuilddirstate(ui, repo, rev, **opts):
3117 def debugrebuilddirstate(ui, repo, rev, **opts):
3092 """rebuild the dirstate as it would look like for the given revision
3118 """rebuild the dirstate as it would look like for the given revision
3093
3119
3094 If no revision is specified the first current parent will be used.
3120 If no revision is specified the first current parent will be used.
3095
3121
3096 The dirstate will be set to the files of the given revision.
3122 The dirstate will be set to the files of the given revision.
3097 The actual working directory content or existing dirstate
3123 The actual working directory content or existing dirstate
3098 information such as adds or removes is not considered.
3124 information such as adds or removes is not considered.
3099
3125
3100 ``minimal`` will only rebuild the dirstate status for files that claim to be
3126 ``minimal`` will only rebuild the dirstate status for files that claim to be
3101 tracked but are not in the parent manifest, or that exist in the parent
3127 tracked but are not in the parent manifest, or that exist in the parent
3102 manifest but are not in the dirstate. It will not change adds, removes, or
3128 manifest but are not in the dirstate. It will not change adds, removes, or
3103 modified files that are in the working copy parent.
3129 modified files that are in the working copy parent.
3104
3130
3105 One use of this command is to make the next :hg:`status` invocation
3131 One use of this command is to make the next :hg:`status` invocation
3106 check the actual file content.
3132 check the actual file content.
3107 """
3133 """
3108 ctx = scmutil.revsingle(repo, rev)
3134 ctx = scmutil.revsingle(repo, rev)
3109 wlock = repo.wlock()
3135 wlock = repo.wlock()
3110 try:
3136 try:
3111 dirstate = repo.dirstate
3137 dirstate = repo.dirstate
3112 changedfiles = None
3138 changedfiles = None
3113 # See command doc for what minimal does.
3139 # See command doc for what minimal does.
3114 if opts.get('minimal'):
3140 if opts.get('minimal'):
3115 manifestfiles = set(ctx.manifest().keys())
3141 manifestfiles = set(ctx.manifest().keys())
3116 dirstatefiles = set(dirstate)
3142 dirstatefiles = set(dirstate)
3117 manifestonly = manifestfiles - dirstatefiles
3143 manifestonly = manifestfiles - dirstatefiles
3118 dsonly = dirstatefiles - manifestfiles
3144 dsonly = dirstatefiles - manifestfiles
3119 dsnotadded = set(f for f in dsonly if dirstate[f] != 'a')
3145 dsnotadded = set(f for f in dsonly if dirstate[f] != 'a')
3120 changedfiles = manifestonly | dsnotadded
3146 changedfiles = manifestonly | dsnotadded
3121
3147
3122 dirstate.rebuild(ctx.node(), ctx.manifest(), changedfiles)
3148 dirstate.rebuild(ctx.node(), ctx.manifest(), changedfiles)
3123 finally:
3149 finally:
3124 wlock.release()
3150 wlock.release()
3125
3151
3126 @command('debugrebuildfncache', [], '')
3152 @command('debugrebuildfncache', [], '')
3127 def debugrebuildfncache(ui, repo):
3153 def debugrebuildfncache(ui, repo):
3128 """rebuild the fncache file"""
3154 """rebuild the fncache file"""
3129 repair.rebuildfncache(ui, repo)
3155 repair.rebuildfncache(ui, repo)
3130
3156
3131 @command('debugrename',
3157 @command('debugrename',
3132 [('r', 'rev', '', _('revision to debug'), _('REV'))],
3158 [('r', 'rev', '', _('revision to debug'), _('REV'))],
3133 _('[-r REV] FILE'))
3159 _('[-r REV] FILE'))
3134 def debugrename(ui, repo, file1, *pats, **opts):
3160 def debugrename(ui, repo, file1, *pats, **opts):
3135 """dump rename information"""
3161 """dump rename information"""
3136
3162
3137 ctx = scmutil.revsingle(repo, opts.get('rev'))
3163 ctx = scmutil.revsingle(repo, opts.get('rev'))
3138 m = scmutil.match(ctx, (file1,) + pats, opts)
3164 m = scmutil.match(ctx, (file1,) + pats, opts)
3139 for abs in ctx.walk(m):
3165 for abs in ctx.walk(m):
3140 fctx = ctx[abs]
3166 fctx = ctx[abs]
3141 o = fctx.filelog().renamed(fctx.filenode())
3167 o = fctx.filelog().renamed(fctx.filenode())
3142 rel = m.rel(abs)
3168 rel = m.rel(abs)
3143 if o:
3169 if o:
3144 ui.write(_("%s renamed from %s:%s\n") % (rel, o[0], hex(o[1])))
3170 ui.write(_("%s renamed from %s:%s\n") % (rel, o[0], hex(o[1])))
3145 else:
3171 else:
3146 ui.write(_("%s not renamed\n") % rel)
3172 ui.write(_("%s not renamed\n") % rel)
3147
3173
3148 @command('debugrevlog', debugrevlogopts +
3174 @command('debugrevlog', debugrevlogopts +
3149 [('d', 'dump', False, _('dump index data'))],
3175 [('d', 'dump', False, _('dump index data'))],
3150 _('-c|-m|FILE'),
3176 _('-c|-m|FILE'),
3151 optionalrepo=True)
3177 optionalrepo=True)
3152 def debugrevlog(ui, repo, file_=None, **opts):
3178 def debugrevlog(ui, repo, file_=None, **opts):
3153 """show data and statistics about a revlog"""
3179 """show data and statistics about a revlog"""
3154 r = cmdutil.openrevlog(repo, 'debugrevlog', file_, opts)
3180 r = cmdutil.openrevlog(repo, 'debugrevlog', file_, opts)
3155
3181
3156 if opts.get("dump"):
3182 if opts.get("dump"):
3157 numrevs = len(r)
3183 numrevs = len(r)
3158 ui.write("# rev p1rev p2rev start end deltastart base p1 p2"
3184 ui.write("# rev p1rev p2rev start end deltastart base p1 p2"
3159 " rawsize totalsize compression heads chainlen\n")
3185 " rawsize totalsize compression heads chainlen\n")
3160 ts = 0
3186 ts = 0
3161 heads = set()
3187 heads = set()
3162
3188
3163 for rev in xrange(numrevs):
3189 for rev in xrange(numrevs):
3164 dbase = r.deltaparent(rev)
3190 dbase = r.deltaparent(rev)
3165 if dbase == -1:
3191 if dbase == -1:
3166 dbase = rev
3192 dbase = rev
3167 cbase = r.chainbase(rev)
3193 cbase = r.chainbase(rev)
3168 clen = r.chainlen(rev)
3194 clen = r.chainlen(rev)
3169 p1, p2 = r.parentrevs(rev)
3195 p1, p2 = r.parentrevs(rev)
3170 rs = r.rawsize(rev)
3196 rs = r.rawsize(rev)
3171 ts = ts + rs
3197 ts = ts + rs
3172 heads -= set(r.parentrevs(rev))
3198 heads -= set(r.parentrevs(rev))
3173 heads.add(rev)
3199 heads.add(rev)
3174 ui.write("%5d %5d %5d %5d %5d %10d %4d %4d %4d %7d %9d "
3200 ui.write("%5d %5d %5d %5d %5d %10d %4d %4d %4d %7d %9d "
3175 "%11d %5d %8d\n" %
3201 "%11d %5d %8d\n" %
3176 (rev, p1, p2, r.start(rev), r.end(rev),
3202 (rev, p1, p2, r.start(rev), r.end(rev),
3177 r.start(dbase), r.start(cbase),
3203 r.start(dbase), r.start(cbase),
3178 r.start(p1), r.start(p2),
3204 r.start(p1), r.start(p2),
3179 rs, ts, ts / r.end(rev), len(heads), clen))
3205 rs, ts, ts / r.end(rev), len(heads), clen))
3180 return 0
3206 return 0
3181
3207
3182 v = r.version
3208 v = r.version
3183 format = v & 0xFFFF
3209 format = v & 0xFFFF
3184 flags = []
3210 flags = []
3185 gdelta = False
3211 gdelta = False
3186 if v & revlog.REVLOGNGINLINEDATA:
3212 if v & revlog.REVLOGNGINLINEDATA:
3187 flags.append('inline')
3213 flags.append('inline')
3188 if v & revlog.REVLOGGENERALDELTA:
3214 if v & revlog.REVLOGGENERALDELTA:
3189 gdelta = True
3215 gdelta = True
3190 flags.append('generaldelta')
3216 flags.append('generaldelta')
3191 if not flags:
3217 if not flags:
3192 flags = ['(none)']
3218 flags = ['(none)']
3193
3219
3194 nummerges = 0
3220 nummerges = 0
3195 numfull = 0
3221 numfull = 0
3196 numprev = 0
3222 numprev = 0
3197 nump1 = 0
3223 nump1 = 0
3198 nump2 = 0
3224 nump2 = 0
3199 numother = 0
3225 numother = 0
3200 nump1prev = 0
3226 nump1prev = 0
3201 nump2prev = 0
3227 nump2prev = 0
3202 chainlengths = []
3228 chainlengths = []
3203
3229
3204 datasize = [None, 0, 0L]
3230 datasize = [None, 0, 0L]
3205 fullsize = [None, 0, 0L]
3231 fullsize = [None, 0, 0L]
3206 deltasize = [None, 0, 0L]
3232 deltasize = [None, 0, 0L]
3207
3233
3208 def addsize(size, l):
3234 def addsize(size, l):
3209 if l[0] is None or size < l[0]:
3235 if l[0] is None or size < l[0]:
3210 l[0] = size
3236 l[0] = size
3211 if size > l[1]:
3237 if size > l[1]:
3212 l[1] = size
3238 l[1] = size
3213 l[2] += size
3239 l[2] += size
3214
3240
3215 numrevs = len(r)
3241 numrevs = len(r)
3216 for rev in xrange(numrevs):
3242 for rev in xrange(numrevs):
3217 p1, p2 = r.parentrevs(rev)
3243 p1, p2 = r.parentrevs(rev)
3218 delta = r.deltaparent(rev)
3244 delta = r.deltaparent(rev)
3219 if format > 0:
3245 if format > 0:
3220 addsize(r.rawsize(rev), datasize)
3246 addsize(r.rawsize(rev), datasize)
3221 if p2 != nullrev:
3247 if p2 != nullrev:
3222 nummerges += 1
3248 nummerges += 1
3223 size = r.length(rev)
3249 size = r.length(rev)
3224 if delta == nullrev:
3250 if delta == nullrev:
3225 chainlengths.append(0)
3251 chainlengths.append(0)
3226 numfull += 1
3252 numfull += 1
3227 addsize(size, fullsize)
3253 addsize(size, fullsize)
3228 else:
3254 else:
3229 chainlengths.append(chainlengths[delta] + 1)
3255 chainlengths.append(chainlengths[delta] + 1)
3230 addsize(size, deltasize)
3256 addsize(size, deltasize)
3231 if delta == rev - 1:
3257 if delta == rev - 1:
3232 numprev += 1
3258 numprev += 1
3233 if delta == p1:
3259 if delta == p1:
3234 nump1prev += 1
3260 nump1prev += 1
3235 elif delta == p2:
3261 elif delta == p2:
3236 nump2prev += 1
3262 nump2prev += 1
3237 elif delta == p1:
3263 elif delta == p1:
3238 nump1 += 1
3264 nump1 += 1
3239 elif delta == p2:
3265 elif delta == p2:
3240 nump2 += 1
3266 nump2 += 1
3241 elif delta != nullrev:
3267 elif delta != nullrev:
3242 numother += 1
3268 numother += 1
3243
3269
3244 # Adjust size min value for empty cases
3270 # Adjust size min value for empty cases
3245 for size in (datasize, fullsize, deltasize):
3271 for size in (datasize, fullsize, deltasize):
3246 if size[0] is None:
3272 if size[0] is None:
3247 size[0] = 0
3273 size[0] = 0
3248
3274
3249 numdeltas = numrevs - numfull
3275 numdeltas = numrevs - numfull
3250 numoprev = numprev - nump1prev - nump2prev
3276 numoprev = numprev - nump1prev - nump2prev
3251 totalrawsize = datasize[2]
3277 totalrawsize = datasize[2]
3252 datasize[2] /= numrevs
3278 datasize[2] /= numrevs
3253 fulltotal = fullsize[2]
3279 fulltotal = fullsize[2]
3254 fullsize[2] /= numfull
3280 fullsize[2] /= numfull
3255 deltatotal = deltasize[2]
3281 deltatotal = deltasize[2]
3256 if numrevs - numfull > 0:
3282 if numrevs - numfull > 0:
3257 deltasize[2] /= numrevs - numfull
3283 deltasize[2] /= numrevs - numfull
3258 totalsize = fulltotal + deltatotal
3284 totalsize = fulltotal + deltatotal
3259 avgchainlen = sum(chainlengths) / numrevs
3285 avgchainlen = sum(chainlengths) / numrevs
3260 maxchainlen = max(chainlengths)
3286 maxchainlen = max(chainlengths)
3261 compratio = 1
3287 compratio = 1
3262 if totalsize:
3288 if totalsize:
3263 compratio = totalrawsize / totalsize
3289 compratio = totalrawsize / totalsize
3264
3290
3265 basedfmtstr = '%%%dd\n'
3291 basedfmtstr = '%%%dd\n'
3266 basepcfmtstr = '%%%dd %s(%%5.2f%%%%)\n'
3292 basepcfmtstr = '%%%dd %s(%%5.2f%%%%)\n'
3267
3293
3268 def dfmtstr(max):
3294 def dfmtstr(max):
3269 return basedfmtstr % len(str(max))
3295 return basedfmtstr % len(str(max))
3270 def pcfmtstr(max, padding=0):
3296 def pcfmtstr(max, padding=0):
3271 return basepcfmtstr % (len(str(max)), ' ' * padding)
3297 return basepcfmtstr % (len(str(max)), ' ' * padding)
3272
3298
3273 def pcfmt(value, total):
3299 def pcfmt(value, total):
3274 if total:
3300 if total:
3275 return (value, 100 * float(value) / total)
3301 return (value, 100 * float(value) / total)
3276 else:
3302 else:
3277 return value, 100.0
3303 return value, 100.0
3278
3304
3279 ui.write(('format : %d\n') % format)
3305 ui.write(('format : %d\n') % format)
3280 ui.write(('flags : %s\n') % ', '.join(flags))
3306 ui.write(('flags : %s\n') % ', '.join(flags))
3281
3307
3282 ui.write('\n')
3308 ui.write('\n')
3283 fmt = pcfmtstr(totalsize)
3309 fmt = pcfmtstr(totalsize)
3284 fmt2 = dfmtstr(totalsize)
3310 fmt2 = dfmtstr(totalsize)
3285 ui.write(('revisions : ') + fmt2 % numrevs)
3311 ui.write(('revisions : ') + fmt2 % numrevs)
3286 ui.write((' merges : ') + fmt % pcfmt(nummerges, numrevs))
3312 ui.write((' merges : ') + fmt % pcfmt(nummerges, numrevs))
3287 ui.write((' normal : ') + fmt % pcfmt(numrevs - nummerges, numrevs))
3313 ui.write((' normal : ') + fmt % pcfmt(numrevs - nummerges, numrevs))
3288 ui.write(('revisions : ') + fmt2 % numrevs)
3314 ui.write(('revisions : ') + fmt2 % numrevs)
3289 ui.write((' full : ') + fmt % pcfmt(numfull, numrevs))
3315 ui.write((' full : ') + fmt % pcfmt(numfull, numrevs))
3290 ui.write((' deltas : ') + fmt % pcfmt(numdeltas, numrevs))
3316 ui.write((' deltas : ') + fmt % pcfmt(numdeltas, numrevs))
3291 ui.write(('revision size : ') + fmt2 % totalsize)
3317 ui.write(('revision size : ') + fmt2 % totalsize)
3292 ui.write((' full : ') + fmt % pcfmt(fulltotal, totalsize))
3318 ui.write((' full : ') + fmt % pcfmt(fulltotal, totalsize))
3293 ui.write((' deltas : ') + fmt % pcfmt(deltatotal, totalsize))
3319 ui.write((' deltas : ') + fmt % pcfmt(deltatotal, totalsize))
3294
3320
3295 ui.write('\n')
3321 ui.write('\n')
3296 fmt = dfmtstr(max(avgchainlen, compratio))
3322 fmt = dfmtstr(max(avgchainlen, compratio))
3297 ui.write(('avg chain length : ') + fmt % avgchainlen)
3323 ui.write(('avg chain length : ') + fmt % avgchainlen)
3298 ui.write(('max chain length : ') + fmt % maxchainlen)
3324 ui.write(('max chain length : ') + fmt % maxchainlen)
3299 ui.write(('compression ratio : ') + fmt % compratio)
3325 ui.write(('compression ratio : ') + fmt % compratio)
3300
3326
3301 if format > 0:
3327 if format > 0:
3302 ui.write('\n')
3328 ui.write('\n')
3303 ui.write(('uncompressed data size (min/max/avg) : %d / %d / %d\n')
3329 ui.write(('uncompressed data size (min/max/avg) : %d / %d / %d\n')
3304 % tuple(datasize))
3330 % tuple(datasize))
3305 ui.write(('full revision size (min/max/avg) : %d / %d / %d\n')
3331 ui.write(('full revision size (min/max/avg) : %d / %d / %d\n')
3306 % tuple(fullsize))
3332 % tuple(fullsize))
3307 ui.write(('delta size (min/max/avg) : %d / %d / %d\n')
3333 ui.write(('delta size (min/max/avg) : %d / %d / %d\n')
3308 % tuple(deltasize))
3334 % tuple(deltasize))
3309
3335
3310 if numdeltas > 0:
3336 if numdeltas > 0:
3311 ui.write('\n')
3337 ui.write('\n')
3312 fmt = pcfmtstr(numdeltas)
3338 fmt = pcfmtstr(numdeltas)
3313 fmt2 = pcfmtstr(numdeltas, 4)
3339 fmt2 = pcfmtstr(numdeltas, 4)
3314 ui.write(('deltas against prev : ') + fmt % pcfmt(numprev, numdeltas))
3340 ui.write(('deltas against prev : ') + fmt % pcfmt(numprev, numdeltas))
3315 if numprev > 0:
3341 if numprev > 0:
3316 ui.write((' where prev = p1 : ') + fmt2 % pcfmt(nump1prev,
3342 ui.write((' where prev = p1 : ') + fmt2 % pcfmt(nump1prev,
3317 numprev))
3343 numprev))
3318 ui.write((' where prev = p2 : ') + fmt2 % pcfmt(nump2prev,
3344 ui.write((' where prev = p2 : ') + fmt2 % pcfmt(nump2prev,
3319 numprev))
3345 numprev))
3320 ui.write((' other : ') + fmt2 % pcfmt(numoprev,
3346 ui.write((' other : ') + fmt2 % pcfmt(numoprev,
3321 numprev))
3347 numprev))
3322 if gdelta:
3348 if gdelta:
3323 ui.write(('deltas against p1 : ')
3349 ui.write(('deltas against p1 : ')
3324 + fmt % pcfmt(nump1, numdeltas))
3350 + fmt % pcfmt(nump1, numdeltas))
3325 ui.write(('deltas against p2 : ')
3351 ui.write(('deltas against p2 : ')
3326 + fmt % pcfmt(nump2, numdeltas))
3352 + fmt % pcfmt(nump2, numdeltas))
3327 ui.write(('deltas against other : ') + fmt % pcfmt(numother,
3353 ui.write(('deltas against other : ') + fmt % pcfmt(numother,
3328 numdeltas))
3354 numdeltas))
3329
3355
3330 @command('debugrevspec',
3356 @command('debugrevspec',
3331 [('', 'optimize', None, _('print parsed tree after optimizing'))],
3357 [('', 'optimize', None, _('print parsed tree after optimizing'))],
3332 ('REVSPEC'))
3358 ('REVSPEC'))
3333 def debugrevspec(ui, repo, expr, **opts):
3359 def debugrevspec(ui, repo, expr, **opts):
3334 """parse and apply a revision specification
3360 """parse and apply a revision specification
3335
3361
3336 Use --verbose to print the parsed tree before and after aliases
3362 Use --verbose to print the parsed tree before and after aliases
3337 expansion.
3363 expansion.
3338 """
3364 """
3339 if ui.verbose:
3365 if ui.verbose:
3340 tree = revset.parse(expr, lookup=repo.__contains__)
3366 tree = revset.parse(expr, lookup=repo.__contains__)
3341 ui.note(revset.prettyformat(tree), "\n")
3367 ui.note(revset.prettyformat(tree), "\n")
3342 newtree = revset.findaliases(ui, tree)
3368 newtree = revset.findaliases(ui, tree)
3343 if newtree != tree:
3369 if newtree != tree:
3344 ui.note(revset.prettyformat(newtree), "\n")
3370 ui.note(revset.prettyformat(newtree), "\n")
3345 tree = newtree
3371 tree = newtree
3346 newtree = revset.foldconcat(tree)
3372 newtree = revset.foldconcat(tree)
3347 if newtree != tree:
3373 if newtree != tree:
3348 ui.note(revset.prettyformat(newtree), "\n")
3374 ui.note(revset.prettyformat(newtree), "\n")
3349 if opts["optimize"]:
3375 if opts["optimize"]:
3350 weight, optimizedtree = revset.optimize(newtree, True)
3376 weight, optimizedtree = revset.optimize(newtree, True)
3351 ui.note("* optimized:\n", revset.prettyformat(optimizedtree), "\n")
3377 ui.note("* optimized:\n", revset.prettyformat(optimizedtree), "\n")
3352 func = revset.match(ui, expr, repo)
3378 func = revset.match(ui, expr, repo)
3353 revs = func(repo)
3379 revs = func(repo)
3354 if ui.verbose:
3380 if ui.verbose:
3355 ui.note("* set:\n", revset.prettyformatset(revs), "\n")
3381 ui.note("* set:\n", revset.prettyformatset(revs), "\n")
3356 for c in revs:
3382 for c in revs:
3357 ui.write("%s\n" % c)
3383 ui.write("%s\n" % c)
3358
3384
3359 @command('debugsetparents', [], _('REV1 [REV2]'))
3385 @command('debugsetparents', [], _('REV1 [REV2]'))
3360 def debugsetparents(ui, repo, rev1, rev2=None):
3386 def debugsetparents(ui, repo, rev1, rev2=None):
3361 """manually set the parents of the current working directory
3387 """manually set the parents of the current working directory
3362
3388
3363 This is useful for writing repository conversion tools, but should
3389 This is useful for writing repository conversion tools, but should
3364 be used with care. For example, neither the working directory nor the
3390 be used with care. For example, neither the working directory nor the
3365 dirstate is updated, so file status may be incorrect after running this
3391 dirstate is updated, so file status may be incorrect after running this
3366 command.
3392 command.
3367
3393
3368 Returns 0 on success.
3394 Returns 0 on success.
3369 """
3395 """
3370
3396
3371 r1 = scmutil.revsingle(repo, rev1).node()
3397 r1 = scmutil.revsingle(repo, rev1).node()
3372 r2 = scmutil.revsingle(repo, rev2, 'null').node()
3398 r2 = scmutil.revsingle(repo, rev2, 'null').node()
3373
3399
3374 wlock = repo.wlock()
3400 wlock = repo.wlock()
3375 try:
3401 try:
3376 repo.dirstate.beginparentchange()
3402 repo.dirstate.beginparentchange()
3377 repo.setparents(r1, r2)
3403 repo.setparents(r1, r2)
3378 repo.dirstate.endparentchange()
3404 repo.dirstate.endparentchange()
3379 finally:
3405 finally:
3380 wlock.release()
3406 wlock.release()
3381
3407
3382 @command('debugdirstate|debugstate',
3408 @command('debugdirstate|debugstate',
3383 [('', 'nodates', None, _('do not display the saved mtime')),
3409 [('', 'nodates', None, _('do not display the saved mtime')),
3384 ('', 'datesort', None, _('sort by saved mtime'))],
3410 ('', 'datesort', None, _('sort by saved mtime'))],
3385 _('[OPTION]...'))
3411 _('[OPTION]...'))
3386 def debugstate(ui, repo, **opts):
3412 def debugstate(ui, repo, **opts):
3387 """show the contents of the current dirstate"""
3413 """show the contents of the current dirstate"""
3388
3414
3389 nodates = opts.get('nodates')
3415 nodates = opts.get('nodates')
3390 datesort = opts.get('datesort')
3416 datesort = opts.get('datesort')
3391
3417
3392 timestr = ""
3418 timestr = ""
3393 if datesort:
3419 if datesort:
3394 keyfunc = lambda x: (x[1][3], x[0]) # sort by mtime, then by filename
3420 keyfunc = lambda x: (x[1][3], x[0]) # sort by mtime, then by filename
3395 else:
3421 else:
3396 keyfunc = None # sort by filename
3422 keyfunc = None # sort by filename
3397 for file_, ent in sorted(repo.dirstate._map.iteritems(), key=keyfunc):
3423 for file_, ent in sorted(repo.dirstate._map.iteritems(), key=keyfunc):
3398 if ent[3] == -1:
3424 if ent[3] == -1:
3399 timestr = 'unset '
3425 timestr = 'unset '
3400 elif nodates:
3426 elif nodates:
3401 timestr = 'set '
3427 timestr = 'set '
3402 else:
3428 else:
3403 timestr = time.strftime("%Y-%m-%d %H:%M:%S ",
3429 timestr = time.strftime("%Y-%m-%d %H:%M:%S ",
3404 time.localtime(ent[3]))
3430 time.localtime(ent[3]))
3405 if ent[1] & 0o20000:
3431 if ent[1] & 0o20000:
3406 mode = 'lnk'
3432 mode = 'lnk'
3407 else:
3433 else:
3408 mode = '%3o' % (ent[1] & 0o777 & ~util.umask)
3434 mode = '%3o' % (ent[1] & 0o777 & ~util.umask)
3409 ui.write("%c %s %10d %s%s\n" % (ent[0], mode, ent[2], timestr, file_))
3435 ui.write("%c %s %10d %s%s\n" % (ent[0], mode, ent[2], timestr, file_))
3410 for f in repo.dirstate.copies():
3436 for f in repo.dirstate.copies():
3411 ui.write(_("copy: %s -> %s\n") % (repo.dirstate.copied(f), f))
3437 ui.write(_("copy: %s -> %s\n") % (repo.dirstate.copied(f), f))
3412
3438
3413 @command('debugsub',
3439 @command('debugsub',
3414 [('r', 'rev', '',
3440 [('r', 'rev', '',
3415 _('revision to check'), _('REV'))],
3441 _('revision to check'), _('REV'))],
3416 _('[-r REV] [REV]'))
3442 _('[-r REV] [REV]'))
3417 def debugsub(ui, repo, rev=None):
3443 def debugsub(ui, repo, rev=None):
3418 ctx = scmutil.revsingle(repo, rev, None)
3444 ctx = scmutil.revsingle(repo, rev, None)
3419 for k, v in sorted(ctx.substate.items()):
3445 for k, v in sorted(ctx.substate.items()):
3420 ui.write(('path %s\n') % k)
3446 ui.write(('path %s\n') % k)
3421 ui.write((' source %s\n') % v[0])
3447 ui.write((' source %s\n') % v[0])
3422 ui.write((' revision %s\n') % v[1])
3448 ui.write((' revision %s\n') % v[1])
3423
3449
3424 @command('debugsuccessorssets',
3450 @command('debugsuccessorssets',
3425 [],
3451 [],
3426 _('[REV]'))
3452 _('[REV]'))
3427 def debugsuccessorssets(ui, repo, *revs):
3453 def debugsuccessorssets(ui, repo, *revs):
3428 """show set of successors for revision
3454 """show set of successors for revision
3429
3455
3430 A successors set of changeset A is a consistent group of revisions that
3456 A successors set of changeset A is a consistent group of revisions that
3431 succeed A. It contains non-obsolete changesets only.
3457 succeed A. It contains non-obsolete changesets only.
3432
3458
3433 In most cases a changeset A has a single successors set containing a single
3459 In most cases a changeset A has a single successors set containing a single
3434 successor (changeset A replaced by A').
3460 successor (changeset A replaced by A').
3435
3461
3436 A changeset that is made obsolete with no successors are called "pruned".
3462 A changeset that is made obsolete with no successors are called "pruned".
3437 Such changesets have no successors sets at all.
3463 Such changesets have no successors sets at all.
3438
3464
3439 A changeset that has been "split" will have a successors set containing
3465 A changeset that has been "split" will have a successors set containing
3440 more than one successor.
3466 more than one successor.
3441
3467
3442 A changeset that has been rewritten in multiple different ways is called
3468 A changeset that has been rewritten in multiple different ways is called
3443 "divergent". Such changesets have multiple successor sets (each of which
3469 "divergent". Such changesets have multiple successor sets (each of which
3444 may also be split, i.e. have multiple successors).
3470 may also be split, i.e. have multiple successors).
3445
3471
3446 Results are displayed as follows::
3472 Results are displayed as follows::
3447
3473
3448 <rev1>
3474 <rev1>
3449 <successors-1A>
3475 <successors-1A>
3450 <rev2>
3476 <rev2>
3451 <successors-2A>
3477 <successors-2A>
3452 <successors-2B1> <successors-2B2> <successors-2B3>
3478 <successors-2B1> <successors-2B2> <successors-2B3>
3453
3479
3454 Here rev2 has two possible (i.e. divergent) successors sets. The first
3480 Here rev2 has two possible (i.e. divergent) successors sets. The first
3455 holds one element, whereas the second holds three (i.e. the changeset has
3481 holds one element, whereas the second holds three (i.e. the changeset has
3456 been split).
3482 been split).
3457 """
3483 """
3458 # passed to successorssets caching computation from one call to another
3484 # passed to successorssets caching computation from one call to another
3459 cache = {}
3485 cache = {}
3460 ctx2str = str
3486 ctx2str = str
3461 node2str = short
3487 node2str = short
3462 if ui.debug():
3488 if ui.debug():
3463 def ctx2str(ctx):
3489 def ctx2str(ctx):
3464 return ctx.hex()
3490 return ctx.hex()
3465 node2str = hex
3491 node2str = hex
3466 for rev in scmutil.revrange(repo, revs):
3492 for rev in scmutil.revrange(repo, revs):
3467 ctx = repo[rev]
3493 ctx = repo[rev]
3468 ui.write('%s\n'% ctx2str(ctx))
3494 ui.write('%s\n'% ctx2str(ctx))
3469 for succsset in obsolete.successorssets(repo, ctx.node(), cache):
3495 for succsset in obsolete.successorssets(repo, ctx.node(), cache):
3470 if succsset:
3496 if succsset:
3471 ui.write(' ')
3497 ui.write(' ')
3472 ui.write(node2str(succsset[0]))
3498 ui.write(node2str(succsset[0]))
3473 for node in succsset[1:]:
3499 for node in succsset[1:]:
3474 ui.write(' ')
3500 ui.write(' ')
3475 ui.write(node2str(node))
3501 ui.write(node2str(node))
3476 ui.write('\n')
3502 ui.write('\n')
3477
3503
3478 @command('debugwalk', walkopts, _('[OPTION]... [FILE]...'), inferrepo=True)
3504 @command('debugwalk', walkopts, _('[OPTION]... [FILE]...'), inferrepo=True)
3479 def debugwalk(ui, repo, *pats, **opts):
3505 def debugwalk(ui, repo, *pats, **opts):
3480 """show how files match on given patterns"""
3506 """show how files match on given patterns"""
3481 m = scmutil.match(repo[None], pats, opts)
3507 m = scmutil.match(repo[None], pats, opts)
3482 items = list(repo.walk(m))
3508 items = list(repo.walk(m))
3483 if not items:
3509 if not items:
3484 return
3510 return
3485 f = lambda fn: fn
3511 f = lambda fn: fn
3486 if ui.configbool('ui', 'slash') and os.sep != '/':
3512 if ui.configbool('ui', 'slash') and os.sep != '/':
3487 f = lambda fn: util.normpath(fn)
3513 f = lambda fn: util.normpath(fn)
3488 fmt = 'f %%-%ds %%-%ds %%s' % (
3514 fmt = 'f %%-%ds %%-%ds %%s' % (
3489 max([len(abs) for abs in items]),
3515 max([len(abs) for abs in items]),
3490 max([len(m.rel(abs)) for abs in items]))
3516 max([len(m.rel(abs)) for abs in items]))
3491 for abs in items:
3517 for abs in items:
3492 line = fmt % (abs, f(m.rel(abs)), m.exact(abs) and 'exact' or '')
3518 line = fmt % (abs, f(m.rel(abs)), m.exact(abs) and 'exact' or '')
3493 ui.write("%s\n" % line.rstrip())
3519 ui.write("%s\n" % line.rstrip())
3494
3520
3495 @command('debugwireargs',
3521 @command('debugwireargs',
3496 [('', 'three', '', 'three'),
3522 [('', 'three', '', 'three'),
3497 ('', 'four', '', 'four'),
3523 ('', 'four', '', 'four'),
3498 ('', 'five', '', 'five'),
3524 ('', 'five', '', 'five'),
3499 ] + remoteopts,
3525 ] + remoteopts,
3500 _('REPO [OPTIONS]... [ONE [TWO]]'),
3526 _('REPO [OPTIONS]... [ONE [TWO]]'),
3501 norepo=True)
3527 norepo=True)
3502 def debugwireargs(ui, repopath, *vals, **opts):
3528 def debugwireargs(ui, repopath, *vals, **opts):
3503 repo = hg.peer(ui, opts, repopath)
3529 repo = hg.peer(ui, opts, repopath)
3504 for opt in remoteopts:
3530 for opt in remoteopts:
3505 del opts[opt[1]]
3531 del opts[opt[1]]
3506 args = {}
3532 args = {}
3507 for k, v in opts.iteritems():
3533 for k, v in opts.iteritems():
3508 if v:
3534 if v:
3509 args[k] = v
3535 args[k] = v
3510 # run twice to check that we don't mess up the stream for the next command
3536 # run twice to check that we don't mess up the stream for the next command
3511 res1 = repo.debugwireargs(*vals, **args)
3537 res1 = repo.debugwireargs(*vals, **args)
3512 res2 = repo.debugwireargs(*vals, **args)
3538 res2 = repo.debugwireargs(*vals, **args)
3513 ui.write("%s\n" % res1)
3539 ui.write("%s\n" % res1)
3514 if res1 != res2:
3540 if res1 != res2:
3515 ui.warn("%s\n" % res2)
3541 ui.warn("%s\n" % res2)
3516
3542
3517 @command('^diff',
3543 @command('^diff',
3518 [('r', 'rev', [], _('revision'), _('REV')),
3544 [('r', 'rev', [], _('revision'), _('REV')),
3519 ('c', 'change', '', _('change made by revision'), _('REV'))
3545 ('c', 'change', '', _('change made by revision'), _('REV'))
3520 ] + diffopts + diffopts2 + walkopts + subrepoopts,
3546 ] + diffopts + diffopts2 + walkopts + subrepoopts,
3521 _('[OPTION]... ([-c REV] | [-r REV1 [-r REV2]]) [FILE]...'),
3547 _('[OPTION]... ([-c REV] | [-r REV1 [-r REV2]]) [FILE]...'),
3522 inferrepo=True)
3548 inferrepo=True)
3523 def diff(ui, repo, *pats, **opts):
3549 def diff(ui, repo, *pats, **opts):
3524 """diff repository (or selected files)
3550 """diff repository (or selected files)
3525
3551
3526 Show differences between revisions for the specified files.
3552 Show differences between revisions for the specified files.
3527
3553
3528 Differences between files are shown using the unified diff format.
3554 Differences between files are shown using the unified diff format.
3529
3555
3530 .. note::
3556 .. note::
3531
3557
3532 :hg:`diff` may generate unexpected results for merges, as it will
3558 :hg:`diff` may generate unexpected results for merges, as it will
3533 default to comparing against the working directory's first
3559 default to comparing against the working directory's first
3534 parent changeset if no revisions are specified.
3560 parent changeset if no revisions are specified.
3535
3561
3536 When two revision arguments are given, then changes are shown
3562 When two revision arguments are given, then changes are shown
3537 between those revisions. If only one revision is specified then
3563 between those revisions. If only one revision is specified then
3538 that revision is compared to the working directory, and, when no
3564 that revision is compared to the working directory, and, when no
3539 revisions are specified, the working directory files are compared
3565 revisions are specified, the working directory files are compared
3540 to its first parent.
3566 to its first parent.
3541
3567
3542 Alternatively you can specify -c/--change with a revision to see
3568 Alternatively you can specify -c/--change with a revision to see
3543 the changes in that changeset relative to its first parent.
3569 the changes in that changeset relative to its first parent.
3544
3570
3545 Without the -a/--text option, diff will avoid generating diffs of
3571 Without the -a/--text option, diff will avoid generating diffs of
3546 files it detects as binary. With -a, diff will generate a diff
3572 files it detects as binary. With -a, diff will generate a diff
3547 anyway, probably with undesirable results.
3573 anyway, probably with undesirable results.
3548
3574
3549 Use the -g/--git option to generate diffs in the git extended diff
3575 Use the -g/--git option to generate diffs in the git extended diff
3550 format. For more information, read :hg:`help diffs`.
3576 format. For more information, read :hg:`help diffs`.
3551
3577
3552 .. container:: verbose
3578 .. container:: verbose
3553
3579
3554 Examples:
3580 Examples:
3555
3581
3556 - compare a file in the current working directory to its parent::
3582 - compare a file in the current working directory to its parent::
3557
3583
3558 hg diff foo.c
3584 hg diff foo.c
3559
3585
3560 - compare two historical versions of a directory, with rename info::
3586 - compare two historical versions of a directory, with rename info::
3561
3587
3562 hg diff --git -r 1.0:1.2 lib/
3588 hg diff --git -r 1.0:1.2 lib/
3563
3589
3564 - get change stats relative to the last change on some date::
3590 - get change stats relative to the last change on some date::
3565
3591
3566 hg diff --stat -r "date('may 2')"
3592 hg diff --stat -r "date('may 2')"
3567
3593
3568 - diff all newly-added files that contain a keyword::
3594 - diff all newly-added files that contain a keyword::
3569
3595
3570 hg diff "set:added() and grep(GNU)"
3596 hg diff "set:added() and grep(GNU)"
3571
3597
3572 - compare a revision and its parents::
3598 - compare a revision and its parents::
3573
3599
3574 hg diff -c 9353 # compare against first parent
3600 hg diff -c 9353 # compare against first parent
3575 hg diff -r 9353^:9353 # same using revset syntax
3601 hg diff -r 9353^:9353 # same using revset syntax
3576 hg diff -r 9353^2:9353 # compare against the second parent
3602 hg diff -r 9353^2:9353 # compare against the second parent
3577
3603
3578 Returns 0 on success.
3604 Returns 0 on success.
3579 """
3605 """
3580
3606
3581 revs = opts.get('rev')
3607 revs = opts.get('rev')
3582 change = opts.get('change')
3608 change = opts.get('change')
3583 stat = opts.get('stat')
3609 stat = opts.get('stat')
3584 reverse = opts.get('reverse')
3610 reverse = opts.get('reverse')
3585
3611
3586 if revs and change:
3612 if revs and change:
3587 msg = _('cannot specify --rev and --change at the same time')
3613 msg = _('cannot specify --rev and --change at the same time')
3588 raise error.Abort(msg)
3614 raise error.Abort(msg)
3589 elif change:
3615 elif change:
3590 node2 = scmutil.revsingle(repo, change, None).node()
3616 node2 = scmutil.revsingle(repo, change, None).node()
3591 node1 = repo[node2].p1().node()
3617 node1 = repo[node2].p1().node()
3592 else:
3618 else:
3593 node1, node2 = scmutil.revpair(repo, revs)
3619 node1, node2 = scmutil.revpair(repo, revs)
3594
3620
3595 if reverse:
3621 if reverse:
3596 node1, node2 = node2, node1
3622 node1, node2 = node2, node1
3597
3623
3598 diffopts = patch.diffallopts(ui, opts)
3624 diffopts = patch.diffallopts(ui, opts)
3599 m = scmutil.match(repo[node2], pats, opts)
3625 m = scmutil.match(repo[node2], pats, opts)
3600 cmdutil.diffordiffstat(ui, repo, diffopts, node1, node2, m, stat=stat,
3626 cmdutil.diffordiffstat(ui, repo, diffopts, node1, node2, m, stat=stat,
3601 listsubrepos=opts.get('subrepos'),
3627 listsubrepos=opts.get('subrepos'),
3602 root=opts.get('root'))
3628 root=opts.get('root'))
3603
3629
3604 @command('^export',
3630 @command('^export',
3605 [('o', 'output', '',
3631 [('o', 'output', '',
3606 _('print output to file with formatted name'), _('FORMAT')),
3632 _('print output to file with formatted name'), _('FORMAT')),
3607 ('', 'switch-parent', None, _('diff against the second parent')),
3633 ('', 'switch-parent', None, _('diff against the second parent')),
3608 ('r', 'rev', [], _('revisions to export'), _('REV')),
3634 ('r', 'rev', [], _('revisions to export'), _('REV')),
3609 ] + diffopts,
3635 ] + diffopts,
3610 _('[OPTION]... [-o OUTFILESPEC] [-r] [REV]...'))
3636 _('[OPTION]... [-o OUTFILESPEC] [-r] [REV]...'))
3611 def export(ui, repo, *changesets, **opts):
3637 def export(ui, repo, *changesets, **opts):
3612 """dump the header and diffs for one or more changesets
3638 """dump the header and diffs for one or more changesets
3613
3639
3614 Print the changeset header and diffs for one or more revisions.
3640 Print the changeset header and diffs for one or more revisions.
3615 If no revision is given, the parent of the working directory is used.
3641 If no revision is given, the parent of the working directory is used.
3616
3642
3617 The information shown in the changeset header is: author, date,
3643 The information shown in the changeset header is: author, date,
3618 branch name (if non-default), changeset hash, parent(s) and commit
3644 branch name (if non-default), changeset hash, parent(s) and commit
3619 comment.
3645 comment.
3620
3646
3621 .. note::
3647 .. note::
3622
3648
3623 :hg:`export` may generate unexpected diff output for merge
3649 :hg:`export` may generate unexpected diff output for merge
3624 changesets, as it will compare the merge changeset against its
3650 changesets, as it will compare the merge changeset against its
3625 first parent only.
3651 first parent only.
3626
3652
3627 Output may be to a file, in which case the name of the file is
3653 Output may be to a file, in which case the name of the file is
3628 given using a format string. The formatting rules are as follows:
3654 given using a format string. The formatting rules are as follows:
3629
3655
3630 :``%%``: literal "%" character
3656 :``%%``: literal "%" character
3631 :``%H``: changeset hash (40 hexadecimal digits)
3657 :``%H``: changeset hash (40 hexadecimal digits)
3632 :``%N``: number of patches being generated
3658 :``%N``: number of patches being generated
3633 :``%R``: changeset revision number
3659 :``%R``: changeset revision number
3634 :``%b``: basename of the exporting repository
3660 :``%b``: basename of the exporting repository
3635 :``%h``: short-form changeset hash (12 hexadecimal digits)
3661 :``%h``: short-form changeset hash (12 hexadecimal digits)
3636 :``%m``: first line of the commit message (only alphanumeric characters)
3662 :``%m``: first line of the commit message (only alphanumeric characters)
3637 :``%n``: zero-padded sequence number, starting at 1
3663 :``%n``: zero-padded sequence number, starting at 1
3638 :``%r``: zero-padded changeset revision number
3664 :``%r``: zero-padded changeset revision number
3639
3665
3640 Without the -a/--text option, export will avoid generating diffs
3666 Without the -a/--text option, export will avoid generating diffs
3641 of files it detects as binary. With -a, export will generate a
3667 of files it detects as binary. With -a, export will generate a
3642 diff anyway, probably with undesirable results.
3668 diff anyway, probably with undesirable results.
3643
3669
3644 Use the -g/--git option to generate diffs in the git extended diff
3670 Use the -g/--git option to generate diffs in the git extended diff
3645 format. See :hg:`help diffs` for more information.
3671 format. See :hg:`help diffs` for more information.
3646
3672
3647 With the --switch-parent option, the diff will be against the
3673 With the --switch-parent option, the diff will be against the
3648 second parent. It can be useful to review a merge.
3674 second parent. It can be useful to review a merge.
3649
3675
3650 .. container:: verbose
3676 .. container:: verbose
3651
3677
3652 Examples:
3678 Examples:
3653
3679
3654 - use export and import to transplant a bugfix to the current
3680 - use export and import to transplant a bugfix to the current
3655 branch::
3681 branch::
3656
3682
3657 hg export -r 9353 | hg import -
3683 hg export -r 9353 | hg import -
3658
3684
3659 - export all the changesets between two revisions to a file with
3685 - export all the changesets between two revisions to a file with
3660 rename information::
3686 rename information::
3661
3687
3662 hg export --git -r 123:150 > changes.txt
3688 hg export --git -r 123:150 > changes.txt
3663
3689
3664 - split outgoing changes into a series of patches with
3690 - split outgoing changes into a series of patches with
3665 descriptive names::
3691 descriptive names::
3666
3692
3667 hg export -r "outgoing()" -o "%n-%m.patch"
3693 hg export -r "outgoing()" -o "%n-%m.patch"
3668
3694
3669 Returns 0 on success.
3695 Returns 0 on success.
3670 """
3696 """
3671 changesets += tuple(opts.get('rev', []))
3697 changesets += tuple(opts.get('rev', []))
3672 if not changesets:
3698 if not changesets:
3673 changesets = ['.']
3699 changesets = ['.']
3674 revs = scmutil.revrange(repo, changesets)
3700 revs = scmutil.revrange(repo, changesets)
3675 if not revs:
3701 if not revs:
3676 raise error.Abort(_("export requires at least one changeset"))
3702 raise error.Abort(_("export requires at least one changeset"))
3677 if len(revs) > 1:
3703 if len(revs) > 1:
3678 ui.note(_('exporting patches:\n'))
3704 ui.note(_('exporting patches:\n'))
3679 else:
3705 else:
3680 ui.note(_('exporting patch:\n'))
3706 ui.note(_('exporting patch:\n'))
3681 cmdutil.export(repo, revs, template=opts.get('output'),
3707 cmdutil.export(repo, revs, template=opts.get('output'),
3682 switch_parent=opts.get('switch_parent'),
3708 switch_parent=opts.get('switch_parent'),
3683 opts=patch.diffallopts(ui, opts))
3709 opts=patch.diffallopts(ui, opts))
3684
3710
3685 @command('files',
3711 @command('files',
3686 [('r', 'rev', '', _('search the repository as it is in REV'), _('REV')),
3712 [('r', 'rev', '', _('search the repository as it is in REV'), _('REV')),
3687 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
3713 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
3688 ] + walkopts + formatteropts + subrepoopts,
3714 ] + walkopts + formatteropts + subrepoopts,
3689 _('[OPTION]... [PATTERN]...'))
3715 _('[OPTION]... [PATTERN]...'))
3690 def files(ui, repo, *pats, **opts):
3716 def files(ui, repo, *pats, **opts):
3691 """list tracked files
3717 """list tracked files
3692
3718
3693 Print files under Mercurial control in the working directory or
3719 Print files under Mercurial control in the working directory or
3694 specified revision whose names match the given patterns (excluding
3720 specified revision whose names match the given patterns (excluding
3695 removed files).
3721 removed files).
3696
3722
3697 If no patterns are given to match, this command prints the names
3723 If no patterns are given to match, this command prints the names
3698 of all files under Mercurial control in the working directory.
3724 of all files under Mercurial control in the working directory.
3699
3725
3700 .. container:: verbose
3726 .. container:: verbose
3701
3727
3702 Examples:
3728 Examples:
3703
3729
3704 - list all files under the current directory::
3730 - list all files under the current directory::
3705
3731
3706 hg files .
3732 hg files .
3707
3733
3708 - shows sizes and flags for current revision::
3734 - shows sizes and flags for current revision::
3709
3735
3710 hg files -vr .
3736 hg files -vr .
3711
3737
3712 - list all files named README::
3738 - list all files named README::
3713
3739
3714 hg files -I "**/README"
3740 hg files -I "**/README"
3715
3741
3716 - list all binary files::
3742 - list all binary files::
3717
3743
3718 hg files "set:binary()"
3744 hg files "set:binary()"
3719
3745
3720 - find files containing a regular expression::
3746 - find files containing a regular expression::
3721
3747
3722 hg files "set:grep('bob')"
3748 hg files "set:grep('bob')"
3723
3749
3724 - search tracked file contents with xargs and grep::
3750 - search tracked file contents with xargs and grep::
3725
3751
3726 hg files -0 | xargs -0 grep foo
3752 hg files -0 | xargs -0 grep foo
3727
3753
3728 See :hg:`help patterns` and :hg:`help filesets` for more information
3754 See :hg:`help patterns` and :hg:`help filesets` for more information
3729 on specifying file patterns.
3755 on specifying file patterns.
3730
3756
3731 Returns 0 if a match is found, 1 otherwise.
3757 Returns 0 if a match is found, 1 otherwise.
3732
3758
3733 """
3759 """
3734 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
3760 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
3735
3761
3736 end = '\n'
3762 end = '\n'
3737 if opts.get('print0'):
3763 if opts.get('print0'):
3738 end = '\0'
3764 end = '\0'
3739 fm = ui.formatter('files', opts)
3765 fm = ui.formatter('files', opts)
3740 fmt = '%s' + end
3766 fmt = '%s' + end
3741
3767
3742 m = scmutil.match(ctx, pats, opts)
3768 m = scmutil.match(ctx, pats, opts)
3743 ret = cmdutil.files(ui, ctx, m, fm, fmt, opts.get('subrepos'))
3769 ret = cmdutil.files(ui, ctx, m, fm, fmt, opts.get('subrepos'))
3744
3770
3745 fm.end()
3771 fm.end()
3746
3772
3747 return ret
3773 return ret
3748
3774
3749 @command('^forget', walkopts, _('[OPTION]... FILE...'), inferrepo=True)
3775 @command('^forget', walkopts, _('[OPTION]... FILE...'), inferrepo=True)
3750 def forget(ui, repo, *pats, **opts):
3776 def forget(ui, repo, *pats, **opts):
3751 """forget the specified files on the next commit
3777 """forget the specified files on the next commit
3752
3778
3753 Mark the specified files so they will no longer be tracked
3779 Mark the specified files so they will no longer be tracked
3754 after the next commit.
3780 after the next commit.
3755
3781
3756 This only removes files from the current branch, not from the
3782 This only removes files from the current branch, not from the
3757 entire project history, and it does not delete them from the
3783 entire project history, and it does not delete them from the
3758 working directory.
3784 working directory.
3759
3785
3760 To delete the file from the working directory, see :hg:`remove`.
3786 To delete the file from the working directory, see :hg:`remove`.
3761
3787
3762 To undo a forget before the next commit, see :hg:`add`.
3788 To undo a forget before the next commit, see :hg:`add`.
3763
3789
3764 .. container:: verbose
3790 .. container:: verbose
3765
3791
3766 Examples:
3792 Examples:
3767
3793
3768 - forget newly-added binary files::
3794 - forget newly-added binary files::
3769
3795
3770 hg forget "set:added() and binary()"
3796 hg forget "set:added() and binary()"
3771
3797
3772 - forget files that would be excluded by .hgignore::
3798 - forget files that would be excluded by .hgignore::
3773
3799
3774 hg forget "set:hgignore()"
3800 hg forget "set:hgignore()"
3775
3801
3776 Returns 0 on success.
3802 Returns 0 on success.
3777 """
3803 """
3778
3804
3779 if not pats:
3805 if not pats:
3780 raise error.Abort(_('no files specified'))
3806 raise error.Abort(_('no files specified'))
3781
3807
3782 m = scmutil.match(repo[None], pats, opts)
3808 m = scmutil.match(repo[None], pats, opts)
3783 rejected = cmdutil.forget(ui, repo, m, prefix="", explicitonly=False)[0]
3809 rejected = cmdutil.forget(ui, repo, m, prefix="", explicitonly=False)[0]
3784 return rejected and 1 or 0
3810 return rejected and 1 or 0
3785
3811
3786 @command(
3812 @command(
3787 'graft',
3813 'graft',
3788 [('r', 'rev', [], _('revisions to graft'), _('REV')),
3814 [('r', 'rev', [], _('revisions to graft'), _('REV')),
3789 ('c', 'continue', False, _('resume interrupted graft')),
3815 ('c', 'continue', False, _('resume interrupted graft')),
3790 ('e', 'edit', False, _('invoke editor on commit messages')),
3816 ('e', 'edit', False, _('invoke editor on commit messages')),
3791 ('', 'log', None, _('append graft info to log message')),
3817 ('', 'log', None, _('append graft info to log message')),
3792 ('f', 'force', False, _('force graft')),
3818 ('f', 'force', False, _('force graft')),
3793 ('D', 'currentdate', False,
3819 ('D', 'currentdate', False,
3794 _('record the current date as commit date')),
3820 _('record the current date as commit date')),
3795 ('U', 'currentuser', False,
3821 ('U', 'currentuser', False,
3796 _('record the current user as committer'), _('DATE'))]
3822 _('record the current user as committer'), _('DATE'))]
3797 + commitopts2 + mergetoolopts + dryrunopts,
3823 + commitopts2 + mergetoolopts + dryrunopts,
3798 _('[OPTION]... [-r] REV...'))
3824 _('[OPTION]... [-r] REV...'))
3799 def graft(ui, repo, *revs, **opts):
3825 def graft(ui, repo, *revs, **opts):
3800 '''copy changes from other branches onto the current branch
3826 '''copy changes from other branches onto the current branch
3801
3827
3802 This command uses Mercurial's merge logic to copy individual
3828 This command uses Mercurial's merge logic to copy individual
3803 changes from other branches without merging branches in the
3829 changes from other branches without merging branches in the
3804 history graph. This is sometimes known as 'backporting' or
3830 history graph. This is sometimes known as 'backporting' or
3805 'cherry-picking'. By default, graft will copy user, date, and
3831 'cherry-picking'. By default, graft will copy user, date, and
3806 description from the source changesets.
3832 description from the source changesets.
3807
3833
3808 Changesets that are ancestors of the current revision, that have
3834 Changesets that are ancestors of the current revision, that have
3809 already been grafted, or that are merges will be skipped.
3835 already been grafted, or that are merges will be skipped.
3810
3836
3811 If --log is specified, log messages will have a comment appended
3837 If --log is specified, log messages will have a comment appended
3812 of the form::
3838 of the form::
3813
3839
3814 (grafted from CHANGESETHASH)
3840 (grafted from CHANGESETHASH)
3815
3841
3816 If --force is specified, revisions will be grafted even if they
3842 If --force is specified, revisions will be grafted even if they
3817 are already ancestors of or have been grafted to the destination.
3843 are already ancestors of or have been grafted to the destination.
3818 This is useful when the revisions have since been backed out.
3844 This is useful when the revisions have since been backed out.
3819
3845
3820 If a graft merge results in conflicts, the graft process is
3846 If a graft merge results in conflicts, the graft process is
3821 interrupted so that the current merge can be manually resolved.
3847 interrupted so that the current merge can be manually resolved.
3822 Once all conflicts are addressed, the graft process can be
3848 Once all conflicts are addressed, the graft process can be
3823 continued with the -c/--continue option.
3849 continued with the -c/--continue option.
3824
3850
3825 .. note::
3851 .. note::
3826
3852
3827 The -c/--continue option does not reapply earlier options, except
3853 The -c/--continue option does not reapply earlier options, except
3828 for --force.
3854 for --force.
3829
3855
3830 .. container:: verbose
3856 .. container:: verbose
3831
3857
3832 Examples:
3858 Examples:
3833
3859
3834 - copy a single change to the stable branch and edit its description::
3860 - copy a single change to the stable branch and edit its description::
3835
3861
3836 hg update stable
3862 hg update stable
3837 hg graft --edit 9393
3863 hg graft --edit 9393
3838
3864
3839 - graft a range of changesets with one exception, updating dates::
3865 - graft a range of changesets with one exception, updating dates::
3840
3866
3841 hg graft -D "2085::2093 and not 2091"
3867 hg graft -D "2085::2093 and not 2091"
3842
3868
3843 - continue a graft after resolving conflicts::
3869 - continue a graft after resolving conflicts::
3844
3870
3845 hg graft -c
3871 hg graft -c
3846
3872
3847 - show the source of a grafted changeset::
3873 - show the source of a grafted changeset::
3848
3874
3849 hg log --debug -r .
3875 hg log --debug -r .
3850
3876
3851 - show revisions sorted by date::
3877 - show revisions sorted by date::
3852
3878
3853 hg log -r 'sort(all(), date)'
3879 hg log -r 'sort(all(), date)'
3854
3880
3855 See :hg:`help revisions` and :hg:`help revsets` for more about
3881 See :hg:`help revisions` and :hg:`help revsets` for more about
3856 specifying revisions.
3882 specifying revisions.
3857
3883
3858 Returns 0 on successful completion.
3884 Returns 0 on successful completion.
3859 '''
3885 '''
3860 wlock = None
3886 wlock = None
3861 try:
3887 try:
3862 wlock = repo.wlock()
3888 wlock = repo.wlock()
3863 return _dograft(ui, repo, *revs, **opts)
3889 return _dograft(ui, repo, *revs, **opts)
3864 finally:
3890 finally:
3865 release(wlock)
3891 release(wlock)
3866
3892
3867 def _dograft(ui, repo, *revs, **opts):
3893 def _dograft(ui, repo, *revs, **opts):
3868 revs = list(revs)
3894 revs = list(revs)
3869 revs.extend(opts['rev'])
3895 revs.extend(opts['rev'])
3870
3896
3871 if not opts.get('user') and opts.get('currentuser'):
3897 if not opts.get('user') and opts.get('currentuser'):
3872 opts['user'] = ui.username()
3898 opts['user'] = ui.username()
3873 if not opts.get('date') and opts.get('currentdate'):
3899 if not opts.get('date') and opts.get('currentdate'):
3874 opts['date'] = "%d %d" % util.makedate()
3900 opts['date'] = "%d %d" % util.makedate()
3875
3901
3876 editor = cmdutil.getcommiteditor(editform='graft', **opts)
3902 editor = cmdutil.getcommiteditor(editform='graft', **opts)
3877
3903
3878 cont = False
3904 cont = False
3879 if opts['continue']:
3905 if opts['continue']:
3880 cont = True
3906 cont = True
3881 if revs:
3907 if revs:
3882 raise error.Abort(_("can't specify --continue and revisions"))
3908 raise error.Abort(_("can't specify --continue and revisions"))
3883 # read in unfinished revisions
3909 # read in unfinished revisions
3884 try:
3910 try:
3885 nodes = repo.vfs.read('graftstate').splitlines()
3911 nodes = repo.vfs.read('graftstate').splitlines()
3886 revs = [repo[node].rev() for node in nodes]
3912 revs = [repo[node].rev() for node in nodes]
3887 except IOError as inst:
3913 except IOError as inst:
3888 if inst.errno != errno.ENOENT:
3914 if inst.errno != errno.ENOENT:
3889 raise
3915 raise
3890 raise error.Abort(_("no graft state found, can't continue"))
3916 raise error.Abort(_("no graft state found, can't continue"))
3891 else:
3917 else:
3892 cmdutil.checkunfinished(repo)
3918 cmdutil.checkunfinished(repo)
3893 cmdutil.bailifchanged(repo)
3919 cmdutil.bailifchanged(repo)
3894 if not revs:
3920 if not revs:
3895 raise error.Abort(_('no revisions specified'))
3921 raise error.Abort(_('no revisions specified'))
3896 revs = scmutil.revrange(repo, revs)
3922 revs = scmutil.revrange(repo, revs)
3897
3923
3898 skipped = set()
3924 skipped = set()
3899 # check for merges
3925 # check for merges
3900 for rev in repo.revs('%ld and merge()', revs):
3926 for rev in repo.revs('%ld and merge()', revs):
3901 ui.warn(_('skipping ungraftable merge revision %s\n') % rev)
3927 ui.warn(_('skipping ungraftable merge revision %s\n') % rev)
3902 skipped.add(rev)
3928 skipped.add(rev)
3903 revs = [r for r in revs if r not in skipped]
3929 revs = [r for r in revs if r not in skipped]
3904 if not revs:
3930 if not revs:
3905 return -1
3931 return -1
3906
3932
3907 # Don't check in the --continue case, in effect retaining --force across
3933 # Don't check in the --continue case, in effect retaining --force across
3908 # --continues. That's because without --force, any revisions we decided to
3934 # --continues. That's because without --force, any revisions we decided to
3909 # skip would have been filtered out here, so they wouldn't have made their
3935 # skip would have been filtered out here, so they wouldn't have made their
3910 # way to the graftstate. With --force, any revisions we would have otherwise
3936 # way to the graftstate. With --force, any revisions we would have otherwise
3911 # skipped would not have been filtered out, and if they hadn't been applied
3937 # skipped would not have been filtered out, and if they hadn't been applied
3912 # already, they'd have been in the graftstate.
3938 # already, they'd have been in the graftstate.
3913 if not (cont or opts.get('force')):
3939 if not (cont or opts.get('force')):
3914 # check for ancestors of dest branch
3940 # check for ancestors of dest branch
3915 crev = repo['.'].rev()
3941 crev = repo['.'].rev()
3916 ancestors = repo.changelog.ancestors([crev], inclusive=True)
3942 ancestors = repo.changelog.ancestors([crev], inclusive=True)
3917 # Cannot use x.remove(y) on smart set, this has to be a list.
3943 # Cannot use x.remove(y) on smart set, this has to be a list.
3918 # XXX make this lazy in the future
3944 # XXX make this lazy in the future
3919 revs = list(revs)
3945 revs = list(revs)
3920 # don't mutate while iterating, create a copy
3946 # don't mutate while iterating, create a copy
3921 for rev in list(revs):
3947 for rev in list(revs):
3922 if rev in ancestors:
3948 if rev in ancestors:
3923 ui.warn(_('skipping ancestor revision %d:%s\n') %
3949 ui.warn(_('skipping ancestor revision %d:%s\n') %
3924 (rev, repo[rev]))
3950 (rev, repo[rev]))
3925 # XXX remove on list is slow
3951 # XXX remove on list is slow
3926 revs.remove(rev)
3952 revs.remove(rev)
3927 if not revs:
3953 if not revs:
3928 return -1
3954 return -1
3929
3955
3930 # analyze revs for earlier grafts
3956 # analyze revs for earlier grafts
3931 ids = {}
3957 ids = {}
3932 for ctx in repo.set("%ld", revs):
3958 for ctx in repo.set("%ld", revs):
3933 ids[ctx.hex()] = ctx.rev()
3959 ids[ctx.hex()] = ctx.rev()
3934 n = ctx.extra().get('source')
3960 n = ctx.extra().get('source')
3935 if n:
3961 if n:
3936 ids[n] = ctx.rev()
3962 ids[n] = ctx.rev()
3937
3963
3938 # check ancestors for earlier grafts
3964 # check ancestors for earlier grafts
3939 ui.debug('scanning for duplicate grafts\n')
3965 ui.debug('scanning for duplicate grafts\n')
3940
3966
3941 for rev in repo.changelog.findmissingrevs(revs, [crev]):
3967 for rev in repo.changelog.findmissingrevs(revs, [crev]):
3942 ctx = repo[rev]
3968 ctx = repo[rev]
3943 n = ctx.extra().get('source')
3969 n = ctx.extra().get('source')
3944 if n in ids:
3970 if n in ids:
3945 try:
3971 try:
3946 r = repo[n].rev()
3972 r = repo[n].rev()
3947 except error.RepoLookupError:
3973 except error.RepoLookupError:
3948 r = None
3974 r = None
3949 if r in revs:
3975 if r in revs:
3950 ui.warn(_('skipping revision %d:%s '
3976 ui.warn(_('skipping revision %d:%s '
3951 '(already grafted to %d:%s)\n')
3977 '(already grafted to %d:%s)\n')
3952 % (r, repo[r], rev, ctx))
3978 % (r, repo[r], rev, ctx))
3953 revs.remove(r)
3979 revs.remove(r)
3954 elif ids[n] in revs:
3980 elif ids[n] in revs:
3955 if r is None:
3981 if r is None:
3956 ui.warn(_('skipping already grafted revision %d:%s '
3982 ui.warn(_('skipping already grafted revision %d:%s '
3957 '(%d:%s also has unknown origin %s)\n')
3983 '(%d:%s also has unknown origin %s)\n')
3958 % (ids[n], repo[ids[n]], rev, ctx, n[:12]))
3984 % (ids[n], repo[ids[n]], rev, ctx, n[:12]))
3959 else:
3985 else:
3960 ui.warn(_('skipping already grafted revision %d:%s '
3986 ui.warn(_('skipping already grafted revision %d:%s '
3961 '(%d:%s also has origin %d:%s)\n')
3987 '(%d:%s also has origin %d:%s)\n')
3962 % (ids[n], repo[ids[n]], rev, ctx, r, n[:12]))
3988 % (ids[n], repo[ids[n]], rev, ctx, r, n[:12]))
3963 revs.remove(ids[n])
3989 revs.remove(ids[n])
3964 elif ctx.hex() in ids:
3990 elif ctx.hex() in ids:
3965 r = ids[ctx.hex()]
3991 r = ids[ctx.hex()]
3966 ui.warn(_('skipping already grafted revision %d:%s '
3992 ui.warn(_('skipping already grafted revision %d:%s '
3967 '(was grafted from %d:%s)\n') %
3993 '(was grafted from %d:%s)\n') %
3968 (r, repo[r], rev, ctx))
3994 (r, repo[r], rev, ctx))
3969 revs.remove(r)
3995 revs.remove(r)
3970 if not revs:
3996 if not revs:
3971 return -1
3997 return -1
3972
3998
3973 try:
3999 try:
3974 for pos, ctx in enumerate(repo.set("%ld", revs)):
4000 for pos, ctx in enumerate(repo.set("%ld", revs)):
3975 desc = '%d:%s "%s"' % (ctx.rev(), ctx,
4001 desc = '%d:%s "%s"' % (ctx.rev(), ctx,
3976 ctx.description().split('\n', 1)[0])
4002 ctx.description().split('\n', 1)[0])
3977 names = repo.nodetags(ctx.node()) + repo.nodebookmarks(ctx.node())
4003 names = repo.nodetags(ctx.node()) + repo.nodebookmarks(ctx.node())
3978 if names:
4004 if names:
3979 desc += ' (%s)' % ' '.join(names)
4005 desc += ' (%s)' % ' '.join(names)
3980 ui.status(_('grafting %s\n') % desc)
4006 ui.status(_('grafting %s\n') % desc)
3981 if opts.get('dry_run'):
4007 if opts.get('dry_run'):
3982 continue
4008 continue
3983
4009
3984 extra = ctx.extra().copy()
4010 extra = ctx.extra().copy()
3985 del extra['branch']
4011 del extra['branch']
3986 source = extra.get('source')
4012 source = extra.get('source')
3987 if source:
4013 if source:
3988 extra['intermediate-source'] = ctx.hex()
4014 extra['intermediate-source'] = ctx.hex()
3989 else:
4015 else:
3990 extra['source'] = ctx.hex()
4016 extra['source'] = ctx.hex()
3991 user = ctx.user()
4017 user = ctx.user()
3992 if opts.get('user'):
4018 if opts.get('user'):
3993 user = opts['user']
4019 user = opts['user']
3994 date = ctx.date()
4020 date = ctx.date()
3995 if opts.get('date'):
4021 if opts.get('date'):
3996 date = opts['date']
4022 date = opts['date']
3997 message = ctx.description()
4023 message = ctx.description()
3998 if opts.get('log'):
4024 if opts.get('log'):
3999 message += '\n(grafted from %s)' % ctx.hex()
4025 message += '\n(grafted from %s)' % ctx.hex()
4000
4026
4001 # we don't merge the first commit when continuing
4027 # we don't merge the first commit when continuing
4002 if not cont:
4028 if not cont:
4003 # perform the graft merge with p1(rev) as 'ancestor'
4029 # perform the graft merge with p1(rev) as 'ancestor'
4004 try:
4030 try:
4005 # ui.forcemerge is an internal variable, do not document
4031 # ui.forcemerge is an internal variable, do not document
4006 repo.ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
4032 repo.ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
4007 'graft')
4033 'graft')
4008 stats = mergemod.graft(repo, ctx, ctx.p1(),
4034 stats = mergemod.graft(repo, ctx, ctx.p1(),
4009 ['local', 'graft'])
4035 ['local', 'graft'])
4010 finally:
4036 finally:
4011 repo.ui.setconfig('ui', 'forcemerge', '', 'graft')
4037 repo.ui.setconfig('ui', 'forcemerge', '', 'graft')
4012 # report any conflicts
4038 # report any conflicts
4013 if stats and stats[3] > 0:
4039 if stats and stats[3] > 0:
4014 # write out state for --continue
4040 # write out state for --continue
4015 nodelines = [repo[rev].hex() + "\n" for rev in revs[pos:]]
4041 nodelines = [repo[rev].hex() + "\n" for rev in revs[pos:]]
4016 repo.vfs.write('graftstate', ''.join(nodelines))
4042 repo.vfs.write('graftstate', ''.join(nodelines))
4017 extra = ''
4043 extra = ''
4018 if opts.get('user'):
4044 if opts.get('user'):
4019 extra += ' --user %s' % opts['user']
4045 extra += ' --user %s' % opts['user']
4020 if opts.get('date'):
4046 if opts.get('date'):
4021 extra += ' --date %s' % opts['date']
4047 extra += ' --date %s' % opts['date']
4022 if opts.get('log'):
4048 if opts.get('log'):
4023 extra += ' --log'
4049 extra += ' --log'
4024 hint=_('use hg resolve and hg graft --continue%s') % extra
4050 hint=_('use hg resolve and hg graft --continue%s') % extra
4025 raise error.Abort(
4051 raise error.Abort(
4026 _("unresolved conflicts, can't continue"),
4052 _("unresolved conflicts, can't continue"),
4027 hint=hint)
4053 hint=hint)
4028 else:
4054 else:
4029 cont = False
4055 cont = False
4030
4056
4031 # commit
4057 # commit
4032 node = repo.commit(text=message, user=user,
4058 node = repo.commit(text=message, user=user,
4033 date=date, extra=extra, editor=editor)
4059 date=date, extra=extra, editor=editor)
4034 if node is None:
4060 if node is None:
4035 ui.warn(
4061 ui.warn(
4036 _('note: graft of %d:%s created no changes to commit\n') %
4062 _('note: graft of %d:%s created no changes to commit\n') %
4037 (ctx.rev(), ctx))
4063 (ctx.rev(), ctx))
4038 finally:
4064 finally:
4039 # TODO: get rid of this meaningless try/finally enclosing.
4065 # TODO: get rid of this meaningless try/finally enclosing.
4040 # this is kept only to reduce changes in a patch.
4066 # this is kept only to reduce changes in a patch.
4041 pass
4067 pass
4042
4068
4043 # remove state when we complete successfully
4069 # remove state when we complete successfully
4044 if not opts.get('dry_run'):
4070 if not opts.get('dry_run'):
4045 util.unlinkpath(repo.join('graftstate'), ignoremissing=True)
4071 util.unlinkpath(repo.join('graftstate'), ignoremissing=True)
4046
4072
4047 return 0
4073 return 0
4048
4074
4049 @command('grep',
4075 @command('grep',
4050 [('0', 'print0', None, _('end fields with NUL')),
4076 [('0', 'print0', None, _('end fields with NUL')),
4051 ('', 'all', None, _('print all revisions that match')),
4077 ('', 'all', None, _('print all revisions that match')),
4052 ('a', 'text', None, _('treat all files as text')),
4078 ('a', 'text', None, _('treat all files as text')),
4053 ('f', 'follow', None,
4079 ('f', 'follow', None,
4054 _('follow changeset history,'
4080 _('follow changeset history,'
4055 ' or file history across copies and renames')),
4081 ' or file history across copies and renames')),
4056 ('i', 'ignore-case', None, _('ignore case when matching')),
4082 ('i', 'ignore-case', None, _('ignore case when matching')),
4057 ('l', 'files-with-matches', None,
4083 ('l', 'files-with-matches', None,
4058 _('print only filenames and revisions that match')),
4084 _('print only filenames and revisions that match')),
4059 ('n', 'line-number', None, _('print matching line numbers')),
4085 ('n', 'line-number', None, _('print matching line numbers')),
4060 ('r', 'rev', [],
4086 ('r', 'rev', [],
4061 _('only search files changed within revision range'), _('REV')),
4087 _('only search files changed within revision range'), _('REV')),
4062 ('u', 'user', None, _('list the author (long with -v)')),
4088 ('u', 'user', None, _('list the author (long with -v)')),
4063 ('d', 'date', None, _('list the date (short with -q)')),
4089 ('d', 'date', None, _('list the date (short with -q)')),
4064 ] + walkopts,
4090 ] + walkopts,
4065 _('[OPTION]... PATTERN [FILE]...'),
4091 _('[OPTION]... PATTERN [FILE]...'),
4066 inferrepo=True)
4092 inferrepo=True)
4067 def grep(ui, repo, pattern, *pats, **opts):
4093 def grep(ui, repo, pattern, *pats, **opts):
4068 """search for a pattern in specified files and revisions
4094 """search for a pattern in specified files and revisions
4069
4095
4070 Search revisions of files for a regular expression.
4096 Search revisions of files for a regular expression.
4071
4097
4072 This command behaves differently than Unix grep. It only accepts
4098 This command behaves differently than Unix grep. It only accepts
4073 Python/Perl regexps. It searches repository history, not the
4099 Python/Perl regexps. It searches repository history, not the
4074 working directory. It always prints the revision number in which a
4100 working directory. It always prints the revision number in which a
4075 match appears.
4101 match appears.
4076
4102
4077 By default, grep only prints output for the first revision of a
4103 By default, grep only prints output for the first revision of a
4078 file in which it finds a match. To get it to print every revision
4104 file in which it finds a match. To get it to print every revision
4079 that contains a change in match status ("-" for a match that
4105 that contains a change in match status ("-" for a match that
4080 becomes a non-match, or "+" for a non-match that becomes a match),
4106 becomes a non-match, or "+" for a non-match that becomes a match),
4081 use the --all flag.
4107 use the --all flag.
4082
4108
4083 Returns 0 if a match is found, 1 otherwise.
4109 Returns 0 if a match is found, 1 otherwise.
4084 """
4110 """
4085 reflags = re.M
4111 reflags = re.M
4086 if opts.get('ignore_case'):
4112 if opts.get('ignore_case'):
4087 reflags |= re.I
4113 reflags |= re.I
4088 try:
4114 try:
4089 regexp = util.re.compile(pattern, reflags)
4115 regexp = util.re.compile(pattern, reflags)
4090 except re.error as inst:
4116 except re.error as inst:
4091 ui.warn(_("grep: invalid match pattern: %s\n") % inst)
4117 ui.warn(_("grep: invalid match pattern: %s\n") % inst)
4092 return 1
4118 return 1
4093 sep, eol = ':', '\n'
4119 sep, eol = ':', '\n'
4094 if opts.get('print0'):
4120 if opts.get('print0'):
4095 sep = eol = '\0'
4121 sep = eol = '\0'
4096
4122
4097 getfile = util.lrucachefunc(repo.file)
4123 getfile = util.lrucachefunc(repo.file)
4098
4124
4099 def matchlines(body):
4125 def matchlines(body):
4100 begin = 0
4126 begin = 0
4101 linenum = 0
4127 linenum = 0
4102 while begin < len(body):
4128 while begin < len(body):
4103 match = regexp.search(body, begin)
4129 match = regexp.search(body, begin)
4104 if not match:
4130 if not match:
4105 break
4131 break
4106 mstart, mend = match.span()
4132 mstart, mend = match.span()
4107 linenum += body.count('\n', begin, mstart) + 1
4133 linenum += body.count('\n', begin, mstart) + 1
4108 lstart = body.rfind('\n', begin, mstart) + 1 or begin
4134 lstart = body.rfind('\n', begin, mstart) + 1 or begin
4109 begin = body.find('\n', mend) + 1 or len(body) + 1
4135 begin = body.find('\n', mend) + 1 or len(body) + 1
4110 lend = begin - 1
4136 lend = begin - 1
4111 yield linenum, mstart - lstart, mend - lstart, body[lstart:lend]
4137 yield linenum, mstart - lstart, mend - lstart, body[lstart:lend]
4112
4138
4113 class linestate(object):
4139 class linestate(object):
4114 def __init__(self, line, linenum, colstart, colend):
4140 def __init__(self, line, linenum, colstart, colend):
4115 self.line = line
4141 self.line = line
4116 self.linenum = linenum
4142 self.linenum = linenum
4117 self.colstart = colstart
4143 self.colstart = colstart
4118 self.colend = colend
4144 self.colend = colend
4119
4145
4120 def __hash__(self):
4146 def __hash__(self):
4121 return hash((self.linenum, self.line))
4147 return hash((self.linenum, self.line))
4122
4148
4123 def __eq__(self, other):
4149 def __eq__(self, other):
4124 return self.line == other.line
4150 return self.line == other.line
4125
4151
4126 def __iter__(self):
4152 def __iter__(self):
4127 yield (self.line[:self.colstart], '')
4153 yield (self.line[:self.colstart], '')
4128 yield (self.line[self.colstart:self.colend], 'grep.match')
4154 yield (self.line[self.colstart:self.colend], 'grep.match')
4129 rest = self.line[self.colend:]
4155 rest = self.line[self.colend:]
4130 while rest != '':
4156 while rest != '':
4131 match = regexp.search(rest)
4157 match = regexp.search(rest)
4132 if not match:
4158 if not match:
4133 yield (rest, '')
4159 yield (rest, '')
4134 break
4160 break
4135 mstart, mend = match.span()
4161 mstart, mend = match.span()
4136 yield (rest[:mstart], '')
4162 yield (rest[:mstart], '')
4137 yield (rest[mstart:mend], 'grep.match')
4163 yield (rest[mstart:mend], 'grep.match')
4138 rest = rest[mend:]
4164 rest = rest[mend:]
4139
4165
4140 matches = {}
4166 matches = {}
4141 copies = {}
4167 copies = {}
4142 def grepbody(fn, rev, body):
4168 def grepbody(fn, rev, body):
4143 matches[rev].setdefault(fn, [])
4169 matches[rev].setdefault(fn, [])
4144 m = matches[rev][fn]
4170 m = matches[rev][fn]
4145 for lnum, cstart, cend, line in matchlines(body):
4171 for lnum, cstart, cend, line in matchlines(body):
4146 s = linestate(line, lnum, cstart, cend)
4172 s = linestate(line, lnum, cstart, cend)
4147 m.append(s)
4173 m.append(s)
4148
4174
4149 def difflinestates(a, b):
4175 def difflinestates(a, b):
4150 sm = difflib.SequenceMatcher(None, a, b)
4176 sm = difflib.SequenceMatcher(None, a, b)
4151 for tag, alo, ahi, blo, bhi in sm.get_opcodes():
4177 for tag, alo, ahi, blo, bhi in sm.get_opcodes():
4152 if tag == 'insert':
4178 if tag == 'insert':
4153 for i in xrange(blo, bhi):
4179 for i in xrange(blo, bhi):
4154 yield ('+', b[i])
4180 yield ('+', b[i])
4155 elif tag == 'delete':
4181 elif tag == 'delete':
4156 for i in xrange(alo, ahi):
4182 for i in xrange(alo, ahi):
4157 yield ('-', a[i])
4183 yield ('-', a[i])
4158 elif tag == 'replace':
4184 elif tag == 'replace':
4159 for i in xrange(alo, ahi):
4185 for i in xrange(alo, ahi):
4160 yield ('-', a[i])
4186 yield ('-', a[i])
4161 for i in xrange(blo, bhi):
4187 for i in xrange(blo, bhi):
4162 yield ('+', b[i])
4188 yield ('+', b[i])
4163
4189
4164 def display(fn, ctx, pstates, states):
4190 def display(fn, ctx, pstates, states):
4165 rev = ctx.rev()
4191 rev = ctx.rev()
4166 if ui.quiet:
4192 if ui.quiet:
4167 datefunc = util.shortdate
4193 datefunc = util.shortdate
4168 else:
4194 else:
4169 datefunc = util.datestr
4195 datefunc = util.datestr
4170 found = False
4196 found = False
4171 @util.cachefunc
4197 @util.cachefunc
4172 def binary():
4198 def binary():
4173 flog = getfile(fn)
4199 flog = getfile(fn)
4174 return util.binary(flog.read(ctx.filenode(fn)))
4200 return util.binary(flog.read(ctx.filenode(fn)))
4175
4201
4176 if opts.get('all'):
4202 if opts.get('all'):
4177 iter = difflinestates(pstates, states)
4203 iter = difflinestates(pstates, states)
4178 else:
4204 else:
4179 iter = [('', l) for l in states]
4205 iter = [('', l) for l in states]
4180 for change, l in iter:
4206 for change, l in iter:
4181 cols = [(fn, 'grep.filename'), (str(rev), 'grep.rev')]
4207 cols = [(fn, 'grep.filename'), (str(rev), 'grep.rev')]
4182
4208
4183 if opts.get('line_number'):
4209 if opts.get('line_number'):
4184 cols.append((str(l.linenum), 'grep.linenumber'))
4210 cols.append((str(l.linenum), 'grep.linenumber'))
4185 if opts.get('all'):
4211 if opts.get('all'):
4186 cols.append((change, 'grep.change'))
4212 cols.append((change, 'grep.change'))
4187 if opts.get('user'):
4213 if opts.get('user'):
4188 cols.append((ui.shortuser(ctx.user()), 'grep.user'))
4214 cols.append((ui.shortuser(ctx.user()), 'grep.user'))
4189 if opts.get('date'):
4215 if opts.get('date'):
4190 cols.append((datefunc(ctx.date()), 'grep.date'))
4216 cols.append((datefunc(ctx.date()), 'grep.date'))
4191 for col, label in cols[:-1]:
4217 for col, label in cols[:-1]:
4192 ui.write(col, label=label)
4218 ui.write(col, label=label)
4193 ui.write(sep, label='grep.sep')
4219 ui.write(sep, label='grep.sep')
4194 ui.write(cols[-1][0], label=cols[-1][1])
4220 ui.write(cols[-1][0], label=cols[-1][1])
4195 if not opts.get('files_with_matches'):
4221 if not opts.get('files_with_matches'):
4196 ui.write(sep, label='grep.sep')
4222 ui.write(sep, label='grep.sep')
4197 if not opts.get('text') and binary():
4223 if not opts.get('text') and binary():
4198 ui.write(" Binary file matches")
4224 ui.write(" Binary file matches")
4199 else:
4225 else:
4200 for s, label in l:
4226 for s, label in l:
4201 ui.write(s, label=label)
4227 ui.write(s, label=label)
4202 ui.write(eol)
4228 ui.write(eol)
4203 found = True
4229 found = True
4204 if opts.get('files_with_matches'):
4230 if opts.get('files_with_matches'):
4205 break
4231 break
4206 return found
4232 return found
4207
4233
4208 skip = {}
4234 skip = {}
4209 revfiles = {}
4235 revfiles = {}
4210 matchfn = scmutil.match(repo[None], pats, opts)
4236 matchfn = scmutil.match(repo[None], pats, opts)
4211 found = False
4237 found = False
4212 follow = opts.get('follow')
4238 follow = opts.get('follow')
4213
4239
4214 def prep(ctx, fns):
4240 def prep(ctx, fns):
4215 rev = ctx.rev()
4241 rev = ctx.rev()
4216 pctx = ctx.p1()
4242 pctx = ctx.p1()
4217 parent = pctx.rev()
4243 parent = pctx.rev()
4218 matches.setdefault(rev, {})
4244 matches.setdefault(rev, {})
4219 matches.setdefault(parent, {})
4245 matches.setdefault(parent, {})
4220 files = revfiles.setdefault(rev, [])
4246 files = revfiles.setdefault(rev, [])
4221 for fn in fns:
4247 for fn in fns:
4222 flog = getfile(fn)
4248 flog = getfile(fn)
4223 try:
4249 try:
4224 fnode = ctx.filenode(fn)
4250 fnode = ctx.filenode(fn)
4225 except error.LookupError:
4251 except error.LookupError:
4226 continue
4252 continue
4227
4253
4228 copied = flog.renamed(fnode)
4254 copied = flog.renamed(fnode)
4229 copy = follow and copied and copied[0]
4255 copy = follow and copied and copied[0]
4230 if copy:
4256 if copy:
4231 copies.setdefault(rev, {})[fn] = copy
4257 copies.setdefault(rev, {})[fn] = copy
4232 if fn in skip:
4258 if fn in skip:
4233 if copy:
4259 if copy:
4234 skip[copy] = True
4260 skip[copy] = True
4235 continue
4261 continue
4236 files.append(fn)
4262 files.append(fn)
4237
4263
4238 if fn not in matches[rev]:
4264 if fn not in matches[rev]:
4239 grepbody(fn, rev, flog.read(fnode))
4265 grepbody(fn, rev, flog.read(fnode))
4240
4266
4241 pfn = copy or fn
4267 pfn = copy or fn
4242 if pfn not in matches[parent]:
4268 if pfn not in matches[parent]:
4243 try:
4269 try:
4244 fnode = pctx.filenode(pfn)
4270 fnode = pctx.filenode(pfn)
4245 grepbody(pfn, parent, flog.read(fnode))
4271 grepbody(pfn, parent, flog.read(fnode))
4246 except error.LookupError:
4272 except error.LookupError:
4247 pass
4273 pass
4248
4274
4249 for ctx in cmdutil.walkchangerevs(repo, matchfn, opts, prep):
4275 for ctx in cmdutil.walkchangerevs(repo, matchfn, opts, prep):
4250 rev = ctx.rev()
4276 rev = ctx.rev()
4251 parent = ctx.p1().rev()
4277 parent = ctx.p1().rev()
4252 for fn in sorted(revfiles.get(rev, [])):
4278 for fn in sorted(revfiles.get(rev, [])):
4253 states = matches[rev][fn]
4279 states = matches[rev][fn]
4254 copy = copies.get(rev, {}).get(fn)
4280 copy = copies.get(rev, {}).get(fn)
4255 if fn in skip:
4281 if fn in skip:
4256 if copy:
4282 if copy:
4257 skip[copy] = True
4283 skip[copy] = True
4258 continue
4284 continue
4259 pstates = matches.get(parent, {}).get(copy or fn, [])
4285 pstates = matches.get(parent, {}).get(copy or fn, [])
4260 if pstates or states:
4286 if pstates or states:
4261 r = display(fn, ctx, pstates, states)
4287 r = display(fn, ctx, pstates, states)
4262 found = found or r
4288 found = found or r
4263 if r and not opts.get('all'):
4289 if r and not opts.get('all'):
4264 skip[fn] = True
4290 skip[fn] = True
4265 if copy:
4291 if copy:
4266 skip[copy] = True
4292 skip[copy] = True
4267 del matches[rev]
4293 del matches[rev]
4268 del revfiles[rev]
4294 del revfiles[rev]
4269
4295
4270 return not found
4296 return not found
4271
4297
4272 @command('heads',
4298 @command('heads',
4273 [('r', 'rev', '',
4299 [('r', 'rev', '',
4274 _('show only heads which are descendants of STARTREV'), _('STARTREV')),
4300 _('show only heads which are descendants of STARTREV'), _('STARTREV')),
4275 ('t', 'topo', False, _('show topological heads only')),
4301 ('t', 'topo', False, _('show topological heads only')),
4276 ('a', 'active', False, _('show active branchheads only (DEPRECATED)')),
4302 ('a', 'active', False, _('show active branchheads only (DEPRECATED)')),
4277 ('c', 'closed', False, _('show normal and closed branch heads')),
4303 ('c', 'closed', False, _('show normal and closed branch heads')),
4278 ] + templateopts,
4304 ] + templateopts,
4279 _('[-ct] [-r STARTREV] [REV]...'))
4305 _('[-ct] [-r STARTREV] [REV]...'))
4280 def heads(ui, repo, *branchrevs, **opts):
4306 def heads(ui, repo, *branchrevs, **opts):
4281 """show branch heads
4307 """show branch heads
4282
4308
4283 With no arguments, show all open branch heads in the repository.
4309 With no arguments, show all open branch heads in the repository.
4284 Branch heads are changesets that have no descendants on the
4310 Branch heads are changesets that have no descendants on the
4285 same branch. They are where development generally takes place and
4311 same branch. They are where development generally takes place and
4286 are the usual targets for update and merge operations.
4312 are the usual targets for update and merge operations.
4287
4313
4288 If one or more REVs are given, only open branch heads on the
4314 If one or more REVs are given, only open branch heads on the
4289 branches associated with the specified changesets are shown. This
4315 branches associated with the specified changesets are shown. This
4290 means that you can use :hg:`heads .` to see the heads on the
4316 means that you can use :hg:`heads .` to see the heads on the
4291 currently checked-out branch.
4317 currently checked-out branch.
4292
4318
4293 If -c/--closed is specified, also show branch heads marked closed
4319 If -c/--closed is specified, also show branch heads marked closed
4294 (see :hg:`commit --close-branch`).
4320 (see :hg:`commit --close-branch`).
4295
4321
4296 If STARTREV is specified, only those heads that are descendants of
4322 If STARTREV is specified, only those heads that are descendants of
4297 STARTREV will be displayed.
4323 STARTREV will be displayed.
4298
4324
4299 If -t/--topo is specified, named branch mechanics will be ignored and only
4325 If -t/--topo is specified, named branch mechanics will be ignored and only
4300 topological heads (changesets with no children) will be shown.
4326 topological heads (changesets with no children) will be shown.
4301
4327
4302 Returns 0 if matching heads are found, 1 if not.
4328 Returns 0 if matching heads are found, 1 if not.
4303 """
4329 """
4304
4330
4305 start = None
4331 start = None
4306 if 'rev' in opts:
4332 if 'rev' in opts:
4307 start = scmutil.revsingle(repo, opts['rev'], None).node()
4333 start = scmutil.revsingle(repo, opts['rev'], None).node()
4308
4334
4309 if opts.get('topo'):
4335 if opts.get('topo'):
4310 heads = [repo[h] for h in repo.heads(start)]
4336 heads = [repo[h] for h in repo.heads(start)]
4311 else:
4337 else:
4312 heads = []
4338 heads = []
4313 for branch in repo.branchmap():
4339 for branch in repo.branchmap():
4314 heads += repo.branchheads(branch, start, opts.get('closed'))
4340 heads += repo.branchheads(branch, start, opts.get('closed'))
4315 heads = [repo[h] for h in heads]
4341 heads = [repo[h] for h in heads]
4316
4342
4317 if branchrevs:
4343 if branchrevs:
4318 branches = set(repo[br].branch() for br in branchrevs)
4344 branches = set(repo[br].branch() for br in branchrevs)
4319 heads = [h for h in heads if h.branch() in branches]
4345 heads = [h for h in heads if h.branch() in branches]
4320
4346
4321 if opts.get('active') and branchrevs:
4347 if opts.get('active') and branchrevs:
4322 dagheads = repo.heads(start)
4348 dagheads = repo.heads(start)
4323 heads = [h for h in heads if h.node() in dagheads]
4349 heads = [h for h in heads if h.node() in dagheads]
4324
4350
4325 if branchrevs:
4351 if branchrevs:
4326 haveheads = set(h.branch() for h in heads)
4352 haveheads = set(h.branch() for h in heads)
4327 if branches - haveheads:
4353 if branches - haveheads:
4328 headless = ', '.join(b for b in branches - haveheads)
4354 headless = ', '.join(b for b in branches - haveheads)
4329 msg = _('no open branch heads found on branches %s')
4355 msg = _('no open branch heads found on branches %s')
4330 if opts.get('rev'):
4356 if opts.get('rev'):
4331 msg += _(' (started at %s)') % opts['rev']
4357 msg += _(' (started at %s)') % opts['rev']
4332 ui.warn((msg + '\n') % headless)
4358 ui.warn((msg + '\n') % headless)
4333
4359
4334 if not heads:
4360 if not heads:
4335 return 1
4361 return 1
4336
4362
4337 heads = sorted(heads, key=lambda x: -x.rev())
4363 heads = sorted(heads, key=lambda x: -x.rev())
4338 displayer = cmdutil.show_changeset(ui, repo, opts)
4364 displayer = cmdutil.show_changeset(ui, repo, opts)
4339 for ctx in heads:
4365 for ctx in heads:
4340 displayer.show(ctx)
4366 displayer.show(ctx)
4341 displayer.close()
4367 displayer.close()
4342
4368
4343 @command('help',
4369 @command('help',
4344 [('e', 'extension', None, _('show only help for extensions')),
4370 [('e', 'extension', None, _('show only help for extensions')),
4345 ('c', 'command', None, _('show only help for commands')),
4371 ('c', 'command', None, _('show only help for commands')),
4346 ('k', 'keyword', None, _('show topics matching keyword')),
4372 ('k', 'keyword', None, _('show topics matching keyword')),
4347 ],
4373 ],
4348 _('[-eck] [TOPIC]'),
4374 _('[-eck] [TOPIC]'),
4349 norepo=True)
4375 norepo=True)
4350 def help_(ui, name=None, **opts):
4376 def help_(ui, name=None, **opts):
4351 """show help for a given topic or a help overview
4377 """show help for a given topic or a help overview
4352
4378
4353 With no arguments, print a list of commands with short help messages.
4379 With no arguments, print a list of commands with short help messages.
4354
4380
4355 Given a topic, extension, or command name, print help for that
4381 Given a topic, extension, or command name, print help for that
4356 topic.
4382 topic.
4357
4383
4358 Returns 0 if successful.
4384 Returns 0 if successful.
4359 """
4385 """
4360
4386
4361 textwidth = min(ui.termwidth(), 80) - 2
4387 textwidth = min(ui.termwidth(), 80) - 2
4362
4388
4363 keep = []
4389 keep = []
4364 if ui.verbose:
4390 if ui.verbose:
4365 keep.append('verbose')
4391 keep.append('verbose')
4366 if sys.platform.startswith('win'):
4392 if sys.platform.startswith('win'):
4367 keep.append('windows')
4393 keep.append('windows')
4368 elif sys.platform == 'OpenVMS':
4394 elif sys.platform == 'OpenVMS':
4369 keep.append('vms')
4395 keep.append('vms')
4370 elif sys.platform == 'plan9':
4396 elif sys.platform == 'plan9':
4371 keep.append('plan9')
4397 keep.append('plan9')
4372 else:
4398 else:
4373 keep.append('unix')
4399 keep.append('unix')
4374 keep.append(sys.platform.lower())
4400 keep.append(sys.platform.lower())
4375
4401
4376 section = None
4402 section = None
4377 subtopic = None
4403 subtopic = None
4378 if name and '.' in name:
4404 if name and '.' in name:
4379 name, section = name.split('.', 1)
4405 name, section = name.split('.', 1)
4380 section = section.lower()
4406 section = section.lower()
4381 if '.' in section:
4407 if '.' in section:
4382 subtopic, section = section.split('.', 1)
4408 subtopic, section = section.split('.', 1)
4383 else:
4409 else:
4384 subtopic = section
4410 subtopic = section
4385
4411
4386 text = help.help_(ui, name, subtopic=subtopic, **opts)
4412 text = help.help_(ui, name, subtopic=subtopic, **opts)
4387
4413
4388 formatted, pruned = minirst.format(text, textwidth, keep=keep,
4414 formatted, pruned = minirst.format(text, textwidth, keep=keep,
4389 section=section)
4415 section=section)
4390
4416
4391 # We could have been given a weird ".foo" section without a name
4417 # We could have been given a weird ".foo" section without a name
4392 # to look for, or we could have simply failed to found "foo.bar"
4418 # to look for, or we could have simply failed to found "foo.bar"
4393 # because bar isn't a section of foo
4419 # because bar isn't a section of foo
4394 if section and not (formatted and name):
4420 if section and not (formatted and name):
4395 raise error.Abort(_("help section not found"))
4421 raise error.Abort(_("help section not found"))
4396
4422
4397 if 'verbose' in pruned:
4423 if 'verbose' in pruned:
4398 keep.append('omitted')
4424 keep.append('omitted')
4399 else:
4425 else:
4400 keep.append('notomitted')
4426 keep.append('notomitted')
4401 formatted, pruned = minirst.format(text, textwidth, keep=keep,
4427 formatted, pruned = minirst.format(text, textwidth, keep=keep,
4402 section=section)
4428 section=section)
4403 ui.write(formatted)
4429 ui.write(formatted)
4404
4430
4405
4431
4406 @command('identify|id',
4432 @command('identify|id',
4407 [('r', 'rev', '',
4433 [('r', 'rev', '',
4408 _('identify the specified revision'), _('REV')),
4434 _('identify the specified revision'), _('REV')),
4409 ('n', 'num', None, _('show local revision number')),
4435 ('n', 'num', None, _('show local revision number')),
4410 ('i', 'id', None, _('show global revision id')),
4436 ('i', 'id', None, _('show global revision id')),
4411 ('b', 'branch', None, _('show branch')),
4437 ('b', 'branch', None, _('show branch')),
4412 ('t', 'tags', None, _('show tags')),
4438 ('t', 'tags', None, _('show tags')),
4413 ('B', 'bookmarks', None, _('show bookmarks')),
4439 ('B', 'bookmarks', None, _('show bookmarks')),
4414 ] + remoteopts,
4440 ] + remoteopts,
4415 _('[-nibtB] [-r REV] [SOURCE]'),
4441 _('[-nibtB] [-r REV] [SOURCE]'),
4416 optionalrepo=True)
4442 optionalrepo=True)
4417 def identify(ui, repo, source=None, rev=None,
4443 def identify(ui, repo, source=None, rev=None,
4418 num=None, id=None, branch=None, tags=None, bookmarks=None, **opts):
4444 num=None, id=None, branch=None, tags=None, bookmarks=None, **opts):
4419 """identify the working directory or specified revision
4445 """identify the working directory or specified revision
4420
4446
4421 Print a summary identifying the repository state at REV using one or
4447 Print a summary identifying the repository state at REV using one or
4422 two parent hash identifiers, followed by a "+" if the working
4448 two parent hash identifiers, followed by a "+" if the working
4423 directory has uncommitted changes, the branch name (if not default),
4449 directory has uncommitted changes, the branch name (if not default),
4424 a list of tags, and a list of bookmarks.
4450 a list of tags, and a list of bookmarks.
4425
4451
4426 When REV is not given, print a summary of the current state of the
4452 When REV is not given, print a summary of the current state of the
4427 repository.
4453 repository.
4428
4454
4429 Specifying a path to a repository root or Mercurial bundle will
4455 Specifying a path to a repository root or Mercurial bundle will
4430 cause lookup to operate on that repository/bundle.
4456 cause lookup to operate on that repository/bundle.
4431
4457
4432 .. container:: verbose
4458 .. container:: verbose
4433
4459
4434 Examples:
4460 Examples:
4435
4461
4436 - generate a build identifier for the working directory::
4462 - generate a build identifier for the working directory::
4437
4463
4438 hg id --id > build-id.dat
4464 hg id --id > build-id.dat
4439
4465
4440 - find the revision corresponding to a tag::
4466 - find the revision corresponding to a tag::
4441
4467
4442 hg id -n -r 1.3
4468 hg id -n -r 1.3
4443
4469
4444 - check the most recent revision of a remote repository::
4470 - check the most recent revision of a remote repository::
4445
4471
4446 hg id -r tip http://selenic.com/hg/
4472 hg id -r tip http://selenic.com/hg/
4447
4473
4448 See :hg:`log` for generating more information about specific revisions,
4474 See :hg:`log` for generating more information about specific revisions,
4449 including full hash identifiers.
4475 including full hash identifiers.
4450
4476
4451 Returns 0 if successful.
4477 Returns 0 if successful.
4452 """
4478 """
4453
4479
4454 if not repo and not source:
4480 if not repo and not source:
4455 raise error.Abort(_("there is no Mercurial repository here "
4481 raise error.Abort(_("there is no Mercurial repository here "
4456 "(.hg not found)"))
4482 "(.hg not found)"))
4457
4483
4458 if ui.debugflag:
4484 if ui.debugflag:
4459 hexfunc = hex
4485 hexfunc = hex
4460 else:
4486 else:
4461 hexfunc = short
4487 hexfunc = short
4462 default = not (num or id or branch or tags or bookmarks)
4488 default = not (num or id or branch or tags or bookmarks)
4463 output = []
4489 output = []
4464 revs = []
4490 revs = []
4465
4491
4466 if source:
4492 if source:
4467 source, branches = hg.parseurl(ui.expandpath(source))
4493 source, branches = hg.parseurl(ui.expandpath(source))
4468 peer = hg.peer(repo or ui, opts, source) # only pass ui when no repo
4494 peer = hg.peer(repo or ui, opts, source) # only pass ui when no repo
4469 repo = peer.local()
4495 repo = peer.local()
4470 revs, checkout = hg.addbranchrevs(repo, peer, branches, None)
4496 revs, checkout = hg.addbranchrevs(repo, peer, branches, None)
4471
4497
4472 if not repo:
4498 if not repo:
4473 if num or branch or tags:
4499 if num or branch or tags:
4474 raise error.Abort(
4500 raise error.Abort(
4475 _("can't query remote revision number, branch, or tags"))
4501 _("can't query remote revision number, branch, or tags"))
4476 if not rev and revs:
4502 if not rev and revs:
4477 rev = revs[0]
4503 rev = revs[0]
4478 if not rev:
4504 if not rev:
4479 rev = "tip"
4505 rev = "tip"
4480
4506
4481 remoterev = peer.lookup(rev)
4507 remoterev = peer.lookup(rev)
4482 if default or id:
4508 if default or id:
4483 output = [hexfunc(remoterev)]
4509 output = [hexfunc(remoterev)]
4484
4510
4485 def getbms():
4511 def getbms():
4486 bms = []
4512 bms = []
4487
4513
4488 if 'bookmarks' in peer.listkeys('namespaces'):
4514 if 'bookmarks' in peer.listkeys('namespaces'):
4489 hexremoterev = hex(remoterev)
4515 hexremoterev = hex(remoterev)
4490 bms = [bm for bm, bmr in peer.listkeys('bookmarks').iteritems()
4516 bms = [bm for bm, bmr in peer.listkeys('bookmarks').iteritems()
4491 if bmr == hexremoterev]
4517 if bmr == hexremoterev]
4492
4518
4493 return sorted(bms)
4519 return sorted(bms)
4494
4520
4495 if bookmarks:
4521 if bookmarks:
4496 output.extend(getbms())
4522 output.extend(getbms())
4497 elif default and not ui.quiet:
4523 elif default and not ui.quiet:
4498 # multiple bookmarks for a single parent separated by '/'
4524 # multiple bookmarks for a single parent separated by '/'
4499 bm = '/'.join(getbms())
4525 bm = '/'.join(getbms())
4500 if bm:
4526 if bm:
4501 output.append(bm)
4527 output.append(bm)
4502 else:
4528 else:
4503 ctx = scmutil.revsingle(repo, rev, None)
4529 ctx = scmutil.revsingle(repo, rev, None)
4504
4530
4505 if ctx.rev() is None:
4531 if ctx.rev() is None:
4506 ctx = repo[None]
4532 ctx = repo[None]
4507 parents = ctx.parents()
4533 parents = ctx.parents()
4508 taglist = []
4534 taglist = []
4509 for p in parents:
4535 for p in parents:
4510 taglist.extend(p.tags())
4536 taglist.extend(p.tags())
4511
4537
4512 changed = ""
4538 changed = ""
4513 if default or id or num:
4539 if default or id or num:
4514 if (any(repo.status())
4540 if (any(repo.status())
4515 or any(ctx.sub(s).dirty() for s in ctx.substate)):
4541 or any(ctx.sub(s).dirty() for s in ctx.substate)):
4516 changed = '+'
4542 changed = '+'
4517 if default or id:
4543 if default or id:
4518 output = ["%s%s" %
4544 output = ["%s%s" %
4519 ('+'.join([hexfunc(p.node()) for p in parents]), changed)]
4545 ('+'.join([hexfunc(p.node()) for p in parents]), changed)]
4520 if num:
4546 if num:
4521 output.append("%s%s" %
4547 output.append("%s%s" %
4522 ('+'.join([str(p.rev()) for p in parents]), changed))
4548 ('+'.join([str(p.rev()) for p in parents]), changed))
4523 else:
4549 else:
4524 if default or id:
4550 if default or id:
4525 output = [hexfunc(ctx.node())]
4551 output = [hexfunc(ctx.node())]
4526 if num:
4552 if num:
4527 output.append(str(ctx.rev()))
4553 output.append(str(ctx.rev()))
4528 taglist = ctx.tags()
4554 taglist = ctx.tags()
4529
4555
4530 if default and not ui.quiet:
4556 if default and not ui.quiet:
4531 b = ctx.branch()
4557 b = ctx.branch()
4532 if b != 'default':
4558 if b != 'default':
4533 output.append("(%s)" % b)
4559 output.append("(%s)" % b)
4534
4560
4535 # multiple tags for a single parent separated by '/'
4561 # multiple tags for a single parent separated by '/'
4536 t = '/'.join(taglist)
4562 t = '/'.join(taglist)
4537 if t:
4563 if t:
4538 output.append(t)
4564 output.append(t)
4539
4565
4540 # multiple bookmarks for a single parent separated by '/'
4566 # multiple bookmarks for a single parent separated by '/'
4541 bm = '/'.join(ctx.bookmarks())
4567 bm = '/'.join(ctx.bookmarks())
4542 if bm:
4568 if bm:
4543 output.append(bm)
4569 output.append(bm)
4544 else:
4570 else:
4545 if branch:
4571 if branch:
4546 output.append(ctx.branch())
4572 output.append(ctx.branch())
4547
4573
4548 if tags:
4574 if tags:
4549 output.extend(taglist)
4575 output.extend(taglist)
4550
4576
4551 if bookmarks:
4577 if bookmarks:
4552 output.extend(ctx.bookmarks())
4578 output.extend(ctx.bookmarks())
4553
4579
4554 ui.write("%s\n" % ' '.join(output))
4580 ui.write("%s\n" % ' '.join(output))
4555
4581
4556 @command('import|patch',
4582 @command('import|patch',
4557 [('p', 'strip', 1,
4583 [('p', 'strip', 1,
4558 _('directory strip option for patch. This has the same '
4584 _('directory strip option for patch. This has the same '
4559 'meaning as the corresponding patch option'), _('NUM')),
4585 'meaning as the corresponding patch option'), _('NUM')),
4560 ('b', 'base', '', _('base path (DEPRECATED)'), _('PATH')),
4586 ('b', 'base', '', _('base path (DEPRECATED)'), _('PATH')),
4561 ('e', 'edit', False, _('invoke editor on commit messages')),
4587 ('e', 'edit', False, _('invoke editor on commit messages')),
4562 ('f', 'force', None,
4588 ('f', 'force', None,
4563 _('skip check for outstanding uncommitted changes (DEPRECATED)')),
4589 _('skip check for outstanding uncommitted changes (DEPRECATED)')),
4564 ('', 'no-commit', None,
4590 ('', 'no-commit', None,
4565 _("don't commit, just update the working directory")),
4591 _("don't commit, just update the working directory")),
4566 ('', 'bypass', None,
4592 ('', 'bypass', None,
4567 _("apply patch without touching the working directory")),
4593 _("apply patch without touching the working directory")),
4568 ('', 'partial', None,
4594 ('', 'partial', None,
4569 _('commit even if some hunks fail')),
4595 _('commit even if some hunks fail')),
4570 ('', 'exact', None,
4596 ('', 'exact', None,
4571 _('apply patch to the nodes from which it was generated')),
4597 _('apply patch to the nodes from which it was generated')),
4572 ('', 'prefix', '',
4598 ('', 'prefix', '',
4573 _('apply patch to subdirectory'), _('DIR')),
4599 _('apply patch to subdirectory'), _('DIR')),
4574 ('', 'import-branch', None,
4600 ('', 'import-branch', None,
4575 _('use any branch information in patch (implied by --exact)'))] +
4601 _('use any branch information in patch (implied by --exact)'))] +
4576 commitopts + commitopts2 + similarityopts,
4602 commitopts + commitopts2 + similarityopts,
4577 _('[OPTION]... PATCH...'))
4603 _('[OPTION]... PATCH...'))
4578 def import_(ui, repo, patch1=None, *patches, **opts):
4604 def import_(ui, repo, patch1=None, *patches, **opts):
4579 """import an ordered set of patches
4605 """import an ordered set of patches
4580
4606
4581 Import a list of patches and commit them individually (unless
4607 Import a list of patches and commit them individually (unless
4582 --no-commit is specified).
4608 --no-commit is specified).
4583
4609
4584 To read a patch from standard input, use "-" as the patch name. If
4610 To read a patch from standard input, use "-" as the patch name. If
4585 a URL is specified, the patch will be downloaded from there.
4611 a URL is specified, the patch will be downloaded from there.
4586
4612
4587 Import first applies changes to the working directory (unless
4613 Import first applies changes to the working directory (unless
4588 --bypass is specified), import will abort if there are outstanding
4614 --bypass is specified), import will abort if there are outstanding
4589 changes.
4615 changes.
4590
4616
4591 Use --bypass to apply and commit patches directly to the
4617 Use --bypass to apply and commit patches directly to the
4592 repository, without affecting the working directory. Without
4618 repository, without affecting the working directory. Without
4593 --exact, patches will be applied on top of the working directory
4619 --exact, patches will be applied on top of the working directory
4594 parent revision.
4620 parent revision.
4595
4621
4596 You can import a patch straight from a mail message. Even patches
4622 You can import a patch straight from a mail message. Even patches
4597 as attachments work (to use the body part, it must have type
4623 as attachments work (to use the body part, it must have type
4598 text/plain or text/x-patch). From and Subject headers of email
4624 text/plain or text/x-patch). From and Subject headers of email
4599 message are used as default committer and commit message. All
4625 message are used as default committer and commit message. All
4600 text/plain body parts before first diff are added to the commit
4626 text/plain body parts before first diff are added to the commit
4601 message.
4627 message.
4602
4628
4603 If the imported patch was generated by :hg:`export`, user and
4629 If the imported patch was generated by :hg:`export`, user and
4604 description from patch override values from message headers and
4630 description from patch override values from message headers and
4605 body. Values given on command line with -m/--message and -u/--user
4631 body. Values given on command line with -m/--message and -u/--user
4606 override these.
4632 override these.
4607
4633
4608 If --exact is specified, import will set the working directory to
4634 If --exact is specified, import will set the working directory to
4609 the parent of each patch before applying it, and will abort if the
4635 the parent of each patch before applying it, and will abort if the
4610 resulting changeset has a different ID than the one recorded in
4636 resulting changeset has a different ID than the one recorded in
4611 the patch. This may happen due to character set problems or other
4637 the patch. This may happen due to character set problems or other
4612 deficiencies in the text patch format.
4638 deficiencies in the text patch format.
4613
4639
4614 Use --partial to ensure a changeset will be created from the patch
4640 Use --partial to ensure a changeset will be created from the patch
4615 even if some hunks fail to apply. Hunks that fail to apply will be
4641 even if some hunks fail to apply. Hunks that fail to apply will be
4616 written to a <target-file>.rej file. Conflicts can then be resolved
4642 written to a <target-file>.rej file. Conflicts can then be resolved
4617 by hand before :hg:`commit --amend` is run to update the created
4643 by hand before :hg:`commit --amend` is run to update the created
4618 changeset. This flag exists to let people import patches that
4644 changeset. This flag exists to let people import patches that
4619 partially apply without losing the associated metadata (author,
4645 partially apply without losing the associated metadata (author,
4620 date, description, ...).
4646 date, description, ...).
4621
4647
4622 .. note::
4648 .. note::
4623
4649
4624 When no hunks apply cleanly, :hg:`import --partial` will create
4650 When no hunks apply cleanly, :hg:`import --partial` will create
4625 an empty changeset, importing only the patch metadata.
4651 an empty changeset, importing only the patch metadata.
4626
4652
4627 With -s/--similarity, hg will attempt to discover renames and
4653 With -s/--similarity, hg will attempt to discover renames and
4628 copies in the patch in the same way as :hg:`addremove`.
4654 copies in the patch in the same way as :hg:`addremove`.
4629
4655
4630 It is possible to use external patch programs to perform the patch
4656 It is possible to use external patch programs to perform the patch
4631 by setting the ``ui.patch`` configuration option. For the default
4657 by setting the ``ui.patch`` configuration option. For the default
4632 internal tool, the fuzz can also be configured via ``patch.fuzz``.
4658 internal tool, the fuzz can also be configured via ``patch.fuzz``.
4633 See :hg:`help config` for more information about configuration
4659 See :hg:`help config` for more information about configuration
4634 files and how to use these options.
4660 files and how to use these options.
4635
4661
4636 See :hg:`help dates` for a list of formats valid for -d/--date.
4662 See :hg:`help dates` for a list of formats valid for -d/--date.
4637
4663
4638 .. container:: verbose
4664 .. container:: verbose
4639
4665
4640 Examples:
4666 Examples:
4641
4667
4642 - import a traditional patch from a website and detect renames::
4668 - import a traditional patch from a website and detect renames::
4643
4669
4644 hg import -s 80 http://example.com/bugfix.patch
4670 hg import -s 80 http://example.com/bugfix.patch
4645
4671
4646 - import a changeset from an hgweb server::
4672 - import a changeset from an hgweb server::
4647
4673
4648 hg import http://www.selenic.com/hg/rev/5ca8c111e9aa
4674 hg import http://www.selenic.com/hg/rev/5ca8c111e9aa
4649
4675
4650 - import all the patches in an Unix-style mbox::
4676 - import all the patches in an Unix-style mbox::
4651
4677
4652 hg import incoming-patches.mbox
4678 hg import incoming-patches.mbox
4653
4679
4654 - attempt to exactly restore an exported changeset (not always
4680 - attempt to exactly restore an exported changeset (not always
4655 possible)::
4681 possible)::
4656
4682
4657 hg import --exact proposed-fix.patch
4683 hg import --exact proposed-fix.patch
4658
4684
4659 - use an external tool to apply a patch which is too fuzzy for
4685 - use an external tool to apply a patch which is too fuzzy for
4660 the default internal tool.
4686 the default internal tool.
4661
4687
4662 hg import --config ui.patch="patch --merge" fuzzy.patch
4688 hg import --config ui.patch="patch --merge" fuzzy.patch
4663
4689
4664 - change the default fuzzing from 2 to a less strict 7
4690 - change the default fuzzing from 2 to a less strict 7
4665
4691
4666 hg import --config ui.fuzz=7 fuzz.patch
4692 hg import --config ui.fuzz=7 fuzz.patch
4667
4693
4668 Returns 0 on success, 1 on partial success (see --partial).
4694 Returns 0 on success, 1 on partial success (see --partial).
4669 """
4695 """
4670
4696
4671 if not patch1:
4697 if not patch1:
4672 raise error.Abort(_('need at least one patch to import'))
4698 raise error.Abort(_('need at least one patch to import'))
4673
4699
4674 patches = (patch1,) + patches
4700 patches = (patch1,) + patches
4675
4701
4676 date = opts.get('date')
4702 date = opts.get('date')
4677 if date:
4703 if date:
4678 opts['date'] = util.parsedate(date)
4704 opts['date'] = util.parsedate(date)
4679
4705
4680 exact = opts.get('exact')
4706 exact = opts.get('exact')
4681 update = not opts.get('bypass')
4707 update = not opts.get('bypass')
4682 if not update and opts.get('no_commit'):
4708 if not update and opts.get('no_commit'):
4683 raise error.Abort(_('cannot use --no-commit with --bypass'))
4709 raise error.Abort(_('cannot use --no-commit with --bypass'))
4684 try:
4710 try:
4685 sim = float(opts.get('similarity') or 0)
4711 sim = float(opts.get('similarity') or 0)
4686 except ValueError:
4712 except ValueError:
4687 raise error.Abort(_('similarity must be a number'))
4713 raise error.Abort(_('similarity must be a number'))
4688 if sim < 0 or sim > 100:
4714 if sim < 0 or sim > 100:
4689 raise error.Abort(_('similarity must be between 0 and 100'))
4715 raise error.Abort(_('similarity must be between 0 and 100'))
4690 if sim and not update:
4716 if sim and not update:
4691 raise error.Abort(_('cannot use --similarity with --bypass'))
4717 raise error.Abort(_('cannot use --similarity with --bypass'))
4692 if exact:
4718 if exact:
4693 if opts.get('edit'):
4719 if opts.get('edit'):
4694 raise error.Abort(_('cannot use --exact with --edit'))
4720 raise error.Abort(_('cannot use --exact with --edit'))
4695 if opts.get('prefix'):
4721 if opts.get('prefix'):
4696 raise error.Abort(_('cannot use --exact with --prefix'))
4722 raise error.Abort(_('cannot use --exact with --prefix'))
4697
4723
4698 base = opts["base"]
4724 base = opts["base"]
4699 wlock = dsguard = lock = tr = None
4725 wlock = dsguard = lock = tr = None
4700 msgs = []
4726 msgs = []
4701 ret = 0
4727 ret = 0
4702
4728
4703
4729
4704 try:
4730 try:
4705 try:
4731 try:
4706 wlock = repo.wlock()
4732 wlock = repo.wlock()
4707
4733
4708 if update:
4734 if update:
4709 cmdutil.checkunfinished(repo)
4735 cmdutil.checkunfinished(repo)
4710 if (exact or not opts.get('force')):
4736 if (exact or not opts.get('force')):
4711 cmdutil.bailifchanged(repo)
4737 cmdutil.bailifchanged(repo)
4712
4738
4713 if not opts.get('no_commit'):
4739 if not opts.get('no_commit'):
4714 lock = repo.lock()
4740 lock = repo.lock()
4715 tr = repo.transaction('import')
4741 tr = repo.transaction('import')
4716 else:
4742 else:
4717 dsguard = cmdutil.dirstateguard(repo, 'import')
4743 dsguard = cmdutil.dirstateguard(repo, 'import')
4718 parents = repo[None].parents()
4744 parents = repo[None].parents()
4719 for patchurl in patches:
4745 for patchurl in patches:
4720 if patchurl == '-':
4746 if patchurl == '-':
4721 ui.status(_('applying patch from stdin\n'))
4747 ui.status(_('applying patch from stdin\n'))
4722 patchfile = ui.fin
4748 patchfile = ui.fin
4723 patchurl = 'stdin' # for error message
4749 patchurl = 'stdin' # for error message
4724 else:
4750 else:
4725 patchurl = os.path.join(base, patchurl)
4751 patchurl = os.path.join(base, patchurl)
4726 ui.status(_('applying %s\n') % patchurl)
4752 ui.status(_('applying %s\n') % patchurl)
4727 patchfile = hg.openpath(ui, patchurl)
4753 patchfile = hg.openpath(ui, patchurl)
4728
4754
4729 haspatch = False
4755 haspatch = False
4730 for hunk in patch.split(patchfile):
4756 for hunk in patch.split(patchfile):
4731 (msg, node, rej) = cmdutil.tryimportone(ui, repo, hunk,
4757 (msg, node, rej) = cmdutil.tryimportone(ui, repo, hunk,
4732 parents, opts,
4758 parents, opts,
4733 msgs, hg.clean)
4759 msgs, hg.clean)
4734 if msg:
4760 if msg:
4735 haspatch = True
4761 haspatch = True
4736 ui.note(msg + '\n')
4762 ui.note(msg + '\n')
4737 if update or exact:
4763 if update or exact:
4738 parents = repo[None].parents()
4764 parents = repo[None].parents()
4739 else:
4765 else:
4740 parents = [repo[node]]
4766 parents = [repo[node]]
4741 if rej:
4767 if rej:
4742 ui.write_err(_("patch applied partially\n"))
4768 ui.write_err(_("patch applied partially\n"))
4743 ui.write_err(_("(fix the .rej files and run "
4769 ui.write_err(_("(fix the .rej files and run "
4744 "`hg commit --amend`)\n"))
4770 "`hg commit --amend`)\n"))
4745 ret = 1
4771 ret = 1
4746 break
4772 break
4747
4773
4748 if not haspatch:
4774 if not haspatch:
4749 raise error.Abort(_('%s: no diffs found') % patchurl)
4775 raise error.Abort(_('%s: no diffs found') % patchurl)
4750
4776
4751 if tr:
4777 if tr:
4752 tr.close()
4778 tr.close()
4753 if msgs:
4779 if msgs:
4754 repo.savecommitmessage('\n* * *\n'.join(msgs))
4780 repo.savecommitmessage('\n* * *\n'.join(msgs))
4755 if dsguard:
4781 if dsguard:
4756 dsguard.close()
4782 dsguard.close()
4757 return ret
4783 return ret
4758 finally:
4784 finally:
4759 # TODO: get rid of this meaningless try/finally enclosing.
4785 # TODO: get rid of this meaningless try/finally enclosing.
4760 # this is kept only to reduce changes in a patch.
4786 # this is kept only to reduce changes in a patch.
4761 pass
4787 pass
4762 finally:
4788 finally:
4763 if tr:
4789 if tr:
4764 tr.release()
4790 tr.release()
4765 release(lock, dsguard, wlock)
4791 release(lock, dsguard, wlock)
4766
4792
4767 @command('incoming|in',
4793 @command('incoming|in',
4768 [('f', 'force', None,
4794 [('f', 'force', None,
4769 _('run even if remote repository is unrelated')),
4795 _('run even if remote repository is unrelated')),
4770 ('n', 'newest-first', None, _('show newest record first')),
4796 ('n', 'newest-first', None, _('show newest record first')),
4771 ('', 'bundle', '',
4797 ('', 'bundle', '',
4772 _('file to store the bundles into'), _('FILE')),
4798 _('file to store the bundles into'), _('FILE')),
4773 ('r', 'rev', [], _('a remote changeset intended to be added'), _('REV')),
4799 ('r', 'rev', [], _('a remote changeset intended to be added'), _('REV')),
4774 ('B', 'bookmarks', False, _("compare bookmarks")),
4800 ('B', 'bookmarks', False, _("compare bookmarks")),
4775 ('b', 'branch', [],
4801 ('b', 'branch', [],
4776 _('a specific branch you would like to pull'), _('BRANCH')),
4802 _('a specific branch you would like to pull'), _('BRANCH')),
4777 ] + logopts + remoteopts + subrepoopts,
4803 ] + logopts + remoteopts + subrepoopts,
4778 _('[-p] [-n] [-M] [-f] [-r REV]... [--bundle FILENAME] [SOURCE]'))
4804 _('[-p] [-n] [-M] [-f] [-r REV]... [--bundle FILENAME] [SOURCE]'))
4779 def incoming(ui, repo, source="default", **opts):
4805 def incoming(ui, repo, source="default", **opts):
4780 """show new changesets found in source
4806 """show new changesets found in source
4781
4807
4782 Show new changesets found in the specified path/URL or the default
4808 Show new changesets found in the specified path/URL or the default
4783 pull location. These are the changesets that would have been pulled
4809 pull location. These are the changesets that would have been pulled
4784 if a pull at the time you issued this command.
4810 if a pull at the time you issued this command.
4785
4811
4786 See pull for valid source format details.
4812 See pull for valid source format details.
4787
4813
4788 .. container:: verbose
4814 .. container:: verbose
4789
4815
4790 With -B/--bookmarks, the result of bookmark comparison between
4816 With -B/--bookmarks, the result of bookmark comparison between
4791 local and remote repositories is displayed. With -v/--verbose,
4817 local and remote repositories is displayed. With -v/--verbose,
4792 status is also displayed for each bookmark like below::
4818 status is also displayed for each bookmark like below::
4793
4819
4794 BM1 01234567890a added
4820 BM1 01234567890a added
4795 BM2 1234567890ab advanced
4821 BM2 1234567890ab advanced
4796 BM3 234567890abc diverged
4822 BM3 234567890abc diverged
4797 BM4 34567890abcd changed
4823 BM4 34567890abcd changed
4798
4824
4799 The action taken locally when pulling depends on the
4825 The action taken locally when pulling depends on the
4800 status of each bookmark:
4826 status of each bookmark:
4801
4827
4802 :``added``: pull will create it
4828 :``added``: pull will create it
4803 :``advanced``: pull will update it
4829 :``advanced``: pull will update it
4804 :``diverged``: pull will create a divergent bookmark
4830 :``diverged``: pull will create a divergent bookmark
4805 :``changed``: result depends on remote changesets
4831 :``changed``: result depends on remote changesets
4806
4832
4807 From the point of view of pulling behavior, bookmark
4833 From the point of view of pulling behavior, bookmark
4808 existing only in the remote repository are treated as ``added``,
4834 existing only in the remote repository are treated as ``added``,
4809 even if it is in fact locally deleted.
4835 even if it is in fact locally deleted.
4810
4836
4811 .. container:: verbose
4837 .. container:: verbose
4812
4838
4813 For remote repository, using --bundle avoids downloading the
4839 For remote repository, using --bundle avoids downloading the
4814 changesets twice if the incoming is followed by a pull.
4840 changesets twice if the incoming is followed by a pull.
4815
4841
4816 Examples:
4842 Examples:
4817
4843
4818 - show incoming changes with patches and full description::
4844 - show incoming changes with patches and full description::
4819
4845
4820 hg incoming -vp
4846 hg incoming -vp
4821
4847
4822 - show incoming changes excluding merges, store a bundle::
4848 - show incoming changes excluding merges, store a bundle::
4823
4849
4824 hg in -vpM --bundle incoming.hg
4850 hg in -vpM --bundle incoming.hg
4825 hg pull incoming.hg
4851 hg pull incoming.hg
4826
4852
4827 - briefly list changes inside a bundle::
4853 - briefly list changes inside a bundle::
4828
4854
4829 hg in changes.hg -T "{desc|firstline}\\n"
4855 hg in changes.hg -T "{desc|firstline}\\n"
4830
4856
4831 Returns 0 if there are incoming changes, 1 otherwise.
4857 Returns 0 if there are incoming changes, 1 otherwise.
4832 """
4858 """
4833 if opts.get('graph'):
4859 if opts.get('graph'):
4834 cmdutil.checkunsupportedgraphflags([], opts)
4860 cmdutil.checkunsupportedgraphflags([], opts)
4835 def display(other, chlist, displayer):
4861 def display(other, chlist, displayer):
4836 revdag = cmdutil.graphrevs(other, chlist, opts)
4862 revdag = cmdutil.graphrevs(other, chlist, opts)
4837 cmdutil.displaygraph(ui, repo, revdag, displayer,
4863 cmdutil.displaygraph(ui, repo, revdag, displayer,
4838 graphmod.asciiedges)
4864 graphmod.asciiedges)
4839
4865
4840 hg._incoming(display, lambda: 1, ui, repo, source, opts, buffered=True)
4866 hg._incoming(display, lambda: 1, ui, repo, source, opts, buffered=True)
4841 return 0
4867 return 0
4842
4868
4843 if opts.get('bundle') and opts.get('subrepos'):
4869 if opts.get('bundle') and opts.get('subrepos'):
4844 raise error.Abort(_('cannot combine --bundle and --subrepos'))
4870 raise error.Abort(_('cannot combine --bundle and --subrepos'))
4845
4871
4846 if opts.get('bookmarks'):
4872 if opts.get('bookmarks'):
4847 source, branches = hg.parseurl(ui.expandpath(source),
4873 source, branches = hg.parseurl(ui.expandpath(source),
4848 opts.get('branch'))
4874 opts.get('branch'))
4849 other = hg.peer(repo, opts, source)
4875 other = hg.peer(repo, opts, source)
4850 if 'bookmarks' not in other.listkeys('namespaces'):
4876 if 'bookmarks' not in other.listkeys('namespaces'):
4851 ui.warn(_("remote doesn't support bookmarks\n"))
4877 ui.warn(_("remote doesn't support bookmarks\n"))
4852 return 0
4878 return 0
4853 ui.status(_('comparing with %s\n') % util.hidepassword(source))
4879 ui.status(_('comparing with %s\n') % util.hidepassword(source))
4854 return bookmarks.incoming(ui, repo, other)
4880 return bookmarks.incoming(ui, repo, other)
4855
4881
4856 repo._subtoppath = ui.expandpath(source)
4882 repo._subtoppath = ui.expandpath(source)
4857 try:
4883 try:
4858 return hg.incoming(ui, repo, source, opts)
4884 return hg.incoming(ui, repo, source, opts)
4859 finally:
4885 finally:
4860 del repo._subtoppath
4886 del repo._subtoppath
4861
4887
4862
4888
4863 @command('^init', remoteopts, _('[-e CMD] [--remotecmd CMD] [DEST]'),
4889 @command('^init', remoteopts, _('[-e CMD] [--remotecmd CMD] [DEST]'),
4864 norepo=True)
4890 norepo=True)
4865 def init(ui, dest=".", **opts):
4891 def init(ui, dest=".", **opts):
4866 """create a new repository in the given directory
4892 """create a new repository in the given directory
4867
4893
4868 Initialize a new repository in the given directory. If the given
4894 Initialize a new repository in the given directory. If the given
4869 directory does not exist, it will be created.
4895 directory does not exist, it will be created.
4870
4896
4871 If no directory is given, the current directory is used.
4897 If no directory is given, the current directory is used.
4872
4898
4873 It is possible to specify an ``ssh://`` URL as the destination.
4899 It is possible to specify an ``ssh://`` URL as the destination.
4874 See :hg:`help urls` for more information.
4900 See :hg:`help urls` for more information.
4875
4901
4876 Returns 0 on success.
4902 Returns 0 on success.
4877 """
4903 """
4878 hg.peer(ui, opts, ui.expandpath(dest), create=True)
4904 hg.peer(ui, opts, ui.expandpath(dest), create=True)
4879
4905
4880 @command('locate',
4906 @command('locate',
4881 [('r', 'rev', '', _('search the repository as it is in REV'), _('REV')),
4907 [('r', 'rev', '', _('search the repository as it is in REV'), _('REV')),
4882 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
4908 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
4883 ('f', 'fullpath', None, _('print complete paths from the filesystem root')),
4909 ('f', 'fullpath', None, _('print complete paths from the filesystem root')),
4884 ] + walkopts,
4910 ] + walkopts,
4885 _('[OPTION]... [PATTERN]...'))
4911 _('[OPTION]... [PATTERN]...'))
4886 def locate(ui, repo, *pats, **opts):
4912 def locate(ui, repo, *pats, **opts):
4887 """locate files matching specific patterns (DEPRECATED)
4913 """locate files matching specific patterns (DEPRECATED)
4888
4914
4889 Print files under Mercurial control in the working directory whose
4915 Print files under Mercurial control in the working directory whose
4890 names match the given patterns.
4916 names match the given patterns.
4891
4917
4892 By default, this command searches all directories in the working
4918 By default, this command searches all directories in the working
4893 directory. To search just the current directory and its
4919 directory. To search just the current directory and its
4894 subdirectories, use "--include .".
4920 subdirectories, use "--include .".
4895
4921
4896 If no patterns are given to match, this command prints the names
4922 If no patterns are given to match, this command prints the names
4897 of all files under Mercurial control in the working directory.
4923 of all files under Mercurial control in the working directory.
4898
4924
4899 If you want to feed the output of this command into the "xargs"
4925 If you want to feed the output of this command into the "xargs"
4900 command, use the -0 option to both this command and "xargs". This
4926 command, use the -0 option to both this command and "xargs". This
4901 will avoid the problem of "xargs" treating single filenames that
4927 will avoid the problem of "xargs" treating single filenames that
4902 contain whitespace as multiple filenames.
4928 contain whitespace as multiple filenames.
4903
4929
4904 See :hg:`help files` for a more versatile command.
4930 See :hg:`help files` for a more versatile command.
4905
4931
4906 Returns 0 if a match is found, 1 otherwise.
4932 Returns 0 if a match is found, 1 otherwise.
4907 """
4933 """
4908 if opts.get('print0'):
4934 if opts.get('print0'):
4909 end = '\0'
4935 end = '\0'
4910 else:
4936 else:
4911 end = '\n'
4937 end = '\n'
4912 rev = scmutil.revsingle(repo, opts.get('rev'), None).node()
4938 rev = scmutil.revsingle(repo, opts.get('rev'), None).node()
4913
4939
4914 ret = 1
4940 ret = 1
4915 ctx = repo[rev]
4941 ctx = repo[rev]
4916 m = scmutil.match(ctx, pats, opts, default='relglob',
4942 m = scmutil.match(ctx, pats, opts, default='relglob',
4917 badfn=lambda x, y: False)
4943 badfn=lambda x, y: False)
4918
4944
4919 for abs in ctx.matches(m):
4945 for abs in ctx.matches(m):
4920 if opts.get('fullpath'):
4946 if opts.get('fullpath'):
4921 ui.write(repo.wjoin(abs), end)
4947 ui.write(repo.wjoin(abs), end)
4922 else:
4948 else:
4923 ui.write(((pats and m.rel(abs)) or abs), end)
4949 ui.write(((pats and m.rel(abs)) or abs), end)
4924 ret = 0
4950 ret = 0
4925
4951
4926 return ret
4952 return ret
4927
4953
4928 @command('^log|history',
4954 @command('^log|history',
4929 [('f', 'follow', None,
4955 [('f', 'follow', None,
4930 _('follow changeset history, or file history across copies and renames')),
4956 _('follow changeset history, or file history across copies and renames')),
4931 ('', 'follow-first', None,
4957 ('', 'follow-first', None,
4932 _('only follow the first parent of merge changesets (DEPRECATED)')),
4958 _('only follow the first parent of merge changesets (DEPRECATED)')),
4933 ('d', 'date', '', _('show revisions matching date spec'), _('DATE')),
4959 ('d', 'date', '', _('show revisions matching date spec'), _('DATE')),
4934 ('C', 'copies', None, _('show copied files')),
4960 ('C', 'copies', None, _('show copied files')),
4935 ('k', 'keyword', [],
4961 ('k', 'keyword', [],
4936 _('do case-insensitive search for a given text'), _('TEXT')),
4962 _('do case-insensitive search for a given text'), _('TEXT')),
4937 ('r', 'rev', [], _('show the specified revision or revset'), _('REV')),
4963 ('r', 'rev', [], _('show the specified revision or revset'), _('REV')),
4938 ('', 'removed', None, _('include revisions where files were removed')),
4964 ('', 'removed', None, _('include revisions where files were removed')),
4939 ('m', 'only-merges', None, _('show only merges (DEPRECATED)')),
4965 ('m', 'only-merges', None, _('show only merges (DEPRECATED)')),
4940 ('u', 'user', [], _('revisions committed by user'), _('USER')),
4966 ('u', 'user', [], _('revisions committed by user'), _('USER')),
4941 ('', 'only-branch', [],
4967 ('', 'only-branch', [],
4942 _('show only changesets within the given named branch (DEPRECATED)'),
4968 _('show only changesets within the given named branch (DEPRECATED)'),
4943 _('BRANCH')),
4969 _('BRANCH')),
4944 ('b', 'branch', [],
4970 ('b', 'branch', [],
4945 _('show changesets within the given named branch'), _('BRANCH')),
4971 _('show changesets within the given named branch'), _('BRANCH')),
4946 ('P', 'prune', [],
4972 ('P', 'prune', [],
4947 _('do not display revision or any of its ancestors'), _('REV')),
4973 _('do not display revision or any of its ancestors'), _('REV')),
4948 ] + logopts + walkopts,
4974 ] + logopts + walkopts,
4949 _('[OPTION]... [FILE]'),
4975 _('[OPTION]... [FILE]'),
4950 inferrepo=True)
4976 inferrepo=True)
4951 def log(ui, repo, *pats, **opts):
4977 def log(ui, repo, *pats, **opts):
4952 """show revision history of entire repository or files
4978 """show revision history of entire repository or files
4953
4979
4954 Print the revision history of the specified files or the entire
4980 Print the revision history of the specified files or the entire
4955 project.
4981 project.
4956
4982
4957 If no revision range is specified, the default is ``tip:0`` unless
4983 If no revision range is specified, the default is ``tip:0`` unless
4958 --follow is set, in which case the working directory parent is
4984 --follow is set, in which case the working directory parent is
4959 used as the starting revision.
4985 used as the starting revision.
4960
4986
4961 File history is shown without following rename or copy history of
4987 File history is shown without following rename or copy history of
4962 files. Use -f/--follow with a filename to follow history across
4988 files. Use -f/--follow with a filename to follow history across
4963 renames and copies. --follow without a filename will only show
4989 renames and copies. --follow without a filename will only show
4964 ancestors or descendants of the starting revision.
4990 ancestors or descendants of the starting revision.
4965
4991
4966 By default this command prints revision number and changeset id,
4992 By default this command prints revision number and changeset id,
4967 tags, non-trivial parents, user, date and time, and a summary for
4993 tags, non-trivial parents, user, date and time, and a summary for
4968 each commit. When the -v/--verbose switch is used, the list of
4994 each commit. When the -v/--verbose switch is used, the list of
4969 changed files and full commit message are shown.
4995 changed files and full commit message are shown.
4970
4996
4971 With --graph the revisions are shown as an ASCII art DAG with the most
4997 With --graph the revisions are shown as an ASCII art DAG with the most
4972 recent changeset at the top.
4998 recent changeset at the top.
4973 'o' is a changeset, '@' is a working directory parent, 'x' is obsolete,
4999 'o' is a changeset, '@' is a working directory parent, 'x' is obsolete,
4974 and '+' represents a fork where the changeset from the lines below is a
5000 and '+' represents a fork where the changeset from the lines below is a
4975 parent of the 'o' merge on the same line.
5001 parent of the 'o' merge on the same line.
4976
5002
4977 .. note::
5003 .. note::
4978
5004
4979 :hg:`log --patch` may generate unexpected diff output for merge
5005 :hg:`log --patch` may generate unexpected diff output for merge
4980 changesets, as it will only compare the merge changeset against
5006 changesets, as it will only compare the merge changeset against
4981 its first parent. Also, only files different from BOTH parents
5007 its first parent. Also, only files different from BOTH parents
4982 will appear in files:.
5008 will appear in files:.
4983
5009
4984 .. note::
5010 .. note::
4985
5011
4986 For performance reasons, :hg:`log FILE` may omit duplicate changes
5012 For performance reasons, :hg:`log FILE` may omit duplicate changes
4987 made on branches and will not show removals or mode changes. To
5013 made on branches and will not show removals or mode changes. To
4988 see all such changes, use the --removed switch.
5014 see all such changes, use the --removed switch.
4989
5015
4990 .. container:: verbose
5016 .. container:: verbose
4991
5017
4992 Some examples:
5018 Some examples:
4993
5019
4994 - changesets with full descriptions and file lists::
5020 - changesets with full descriptions and file lists::
4995
5021
4996 hg log -v
5022 hg log -v
4997
5023
4998 - changesets ancestral to the working directory::
5024 - changesets ancestral to the working directory::
4999
5025
5000 hg log -f
5026 hg log -f
5001
5027
5002 - last 10 commits on the current branch::
5028 - last 10 commits on the current branch::
5003
5029
5004 hg log -l 10 -b .
5030 hg log -l 10 -b .
5005
5031
5006 - changesets showing all modifications of a file, including removals::
5032 - changesets showing all modifications of a file, including removals::
5007
5033
5008 hg log --removed file.c
5034 hg log --removed file.c
5009
5035
5010 - all changesets that touch a directory, with diffs, excluding merges::
5036 - all changesets that touch a directory, with diffs, excluding merges::
5011
5037
5012 hg log -Mp lib/
5038 hg log -Mp lib/
5013
5039
5014 - all revision numbers that match a keyword::
5040 - all revision numbers that match a keyword::
5015
5041
5016 hg log -k bug --template "{rev}\\n"
5042 hg log -k bug --template "{rev}\\n"
5017
5043
5018 - the full hash identifier of the working directory parent::
5044 - the full hash identifier of the working directory parent::
5019
5045
5020 hg log -r . --template "{node}\\n"
5046 hg log -r . --template "{node}\\n"
5021
5047
5022 - list available log templates::
5048 - list available log templates::
5023
5049
5024 hg log -T list
5050 hg log -T list
5025
5051
5026 - check if a given changeset is included in a tagged release::
5052 - check if a given changeset is included in a tagged release::
5027
5053
5028 hg log -r "a21ccf and ancestor(1.9)"
5054 hg log -r "a21ccf and ancestor(1.9)"
5029
5055
5030 - find all changesets by some user in a date range::
5056 - find all changesets by some user in a date range::
5031
5057
5032 hg log -k alice -d "may 2008 to jul 2008"
5058 hg log -k alice -d "may 2008 to jul 2008"
5033
5059
5034 - summary of all changesets after the last tag::
5060 - summary of all changesets after the last tag::
5035
5061
5036 hg log -r "last(tagged())::" --template "{desc|firstline}\\n"
5062 hg log -r "last(tagged())::" --template "{desc|firstline}\\n"
5037
5063
5038 See :hg:`help dates` for a list of formats valid for -d/--date.
5064 See :hg:`help dates` for a list of formats valid for -d/--date.
5039
5065
5040 See :hg:`help revisions` and :hg:`help revsets` for more about
5066 See :hg:`help revisions` and :hg:`help revsets` for more about
5041 specifying and ordering revisions.
5067 specifying and ordering revisions.
5042
5068
5043 See :hg:`help templates` for more about pre-packaged styles and
5069 See :hg:`help templates` for more about pre-packaged styles and
5044 specifying custom templates.
5070 specifying custom templates.
5045
5071
5046 Returns 0 on success.
5072 Returns 0 on success.
5047
5073
5048 """
5074 """
5049 if opts.get('follow') and opts.get('rev'):
5075 if opts.get('follow') and opts.get('rev'):
5050 opts['rev'] = [revset.formatspec('reverse(::%lr)', opts.get('rev'))]
5076 opts['rev'] = [revset.formatspec('reverse(::%lr)', opts.get('rev'))]
5051 del opts['follow']
5077 del opts['follow']
5052
5078
5053 if opts.get('graph'):
5079 if opts.get('graph'):
5054 return cmdutil.graphlog(ui, repo, *pats, **opts)
5080 return cmdutil.graphlog(ui, repo, *pats, **opts)
5055
5081
5056 revs, expr, filematcher = cmdutil.getlogrevs(repo, pats, opts)
5082 revs, expr, filematcher = cmdutil.getlogrevs(repo, pats, opts)
5057 limit = cmdutil.loglimit(opts)
5083 limit = cmdutil.loglimit(opts)
5058 count = 0
5084 count = 0
5059
5085
5060 getrenamed = None
5086 getrenamed = None
5061 if opts.get('copies'):
5087 if opts.get('copies'):
5062 endrev = None
5088 endrev = None
5063 if opts.get('rev'):
5089 if opts.get('rev'):
5064 endrev = scmutil.revrange(repo, opts.get('rev')).max() + 1
5090 endrev = scmutil.revrange(repo, opts.get('rev')).max() + 1
5065 getrenamed = templatekw.getrenamedfn(repo, endrev=endrev)
5091 getrenamed = templatekw.getrenamedfn(repo, endrev=endrev)
5066
5092
5067 displayer = cmdutil.show_changeset(ui, repo, opts, buffered=True)
5093 displayer = cmdutil.show_changeset(ui, repo, opts, buffered=True)
5068 for rev in revs:
5094 for rev in revs:
5069 if count == limit:
5095 if count == limit:
5070 break
5096 break
5071 ctx = repo[rev]
5097 ctx = repo[rev]
5072 copies = None
5098 copies = None
5073 if getrenamed is not None and rev:
5099 if getrenamed is not None and rev:
5074 copies = []
5100 copies = []
5075 for fn in ctx.files():
5101 for fn in ctx.files():
5076 rename = getrenamed(fn, rev)
5102 rename = getrenamed(fn, rev)
5077 if rename:
5103 if rename:
5078 copies.append((fn, rename[0]))
5104 copies.append((fn, rename[0]))
5079 if filematcher:
5105 if filematcher:
5080 revmatchfn = filematcher(ctx.rev())
5106 revmatchfn = filematcher(ctx.rev())
5081 else:
5107 else:
5082 revmatchfn = None
5108 revmatchfn = None
5083 displayer.show(ctx, copies=copies, matchfn=revmatchfn)
5109 displayer.show(ctx, copies=copies, matchfn=revmatchfn)
5084 if displayer.flush(ctx):
5110 if displayer.flush(ctx):
5085 count += 1
5111 count += 1
5086
5112
5087 displayer.close()
5113 displayer.close()
5088
5114
5089 @command('manifest',
5115 @command('manifest',
5090 [('r', 'rev', '', _('revision to display'), _('REV')),
5116 [('r', 'rev', '', _('revision to display'), _('REV')),
5091 ('', 'all', False, _("list files from all revisions"))]
5117 ('', 'all', False, _("list files from all revisions"))]
5092 + formatteropts,
5118 + formatteropts,
5093 _('[-r REV]'))
5119 _('[-r REV]'))
5094 def manifest(ui, repo, node=None, rev=None, **opts):
5120 def manifest(ui, repo, node=None, rev=None, **opts):
5095 """output the current or given revision of the project manifest
5121 """output the current or given revision of the project manifest
5096
5122
5097 Print a list of version controlled files for the given revision.
5123 Print a list of version controlled files for the given revision.
5098 If no revision is given, the first parent of the working directory
5124 If no revision is given, the first parent of the working directory
5099 is used, or the null revision if no revision is checked out.
5125 is used, or the null revision if no revision is checked out.
5100
5126
5101 With -v, print file permissions, symlink and executable bits.
5127 With -v, print file permissions, symlink and executable bits.
5102 With --debug, print file revision hashes.
5128 With --debug, print file revision hashes.
5103
5129
5104 If option --all is specified, the list of all files from all revisions
5130 If option --all is specified, the list of all files from all revisions
5105 is printed. This includes deleted and renamed files.
5131 is printed. This includes deleted and renamed files.
5106
5132
5107 Returns 0 on success.
5133 Returns 0 on success.
5108 """
5134 """
5109
5135
5110 fm = ui.formatter('manifest', opts)
5136 fm = ui.formatter('manifest', opts)
5111
5137
5112 if opts.get('all'):
5138 if opts.get('all'):
5113 if rev or node:
5139 if rev or node:
5114 raise error.Abort(_("can't specify a revision with --all"))
5140 raise error.Abort(_("can't specify a revision with --all"))
5115
5141
5116 res = []
5142 res = []
5117 prefix = "data/"
5143 prefix = "data/"
5118 suffix = ".i"
5144 suffix = ".i"
5119 plen = len(prefix)
5145 plen = len(prefix)
5120 slen = len(suffix)
5146 slen = len(suffix)
5121 lock = repo.lock()
5147 lock = repo.lock()
5122 try:
5148 try:
5123 for fn, b, size in repo.store.datafiles():
5149 for fn, b, size in repo.store.datafiles():
5124 if size != 0 and fn[-slen:] == suffix and fn[:plen] == prefix:
5150 if size != 0 and fn[-slen:] == suffix and fn[:plen] == prefix:
5125 res.append(fn[plen:-slen])
5151 res.append(fn[plen:-slen])
5126 finally:
5152 finally:
5127 lock.release()
5153 lock.release()
5128 for f in res:
5154 for f in res:
5129 fm.startitem()
5155 fm.startitem()
5130 fm.write("path", '%s\n', f)
5156 fm.write("path", '%s\n', f)
5131 fm.end()
5157 fm.end()
5132 return
5158 return
5133
5159
5134 if rev and node:
5160 if rev and node:
5135 raise error.Abort(_("please specify just one revision"))
5161 raise error.Abort(_("please specify just one revision"))
5136
5162
5137 if not node:
5163 if not node:
5138 node = rev
5164 node = rev
5139
5165
5140 char = {'l': '@', 'x': '*', '': ''}
5166 char = {'l': '@', 'x': '*', '': ''}
5141 mode = {'l': '644', 'x': '755', '': '644'}
5167 mode = {'l': '644', 'x': '755', '': '644'}
5142 ctx = scmutil.revsingle(repo, node)
5168 ctx = scmutil.revsingle(repo, node)
5143 mf = ctx.manifest()
5169 mf = ctx.manifest()
5144 for f in ctx:
5170 for f in ctx:
5145 fm.startitem()
5171 fm.startitem()
5146 fl = ctx[f].flags()
5172 fl = ctx[f].flags()
5147 fm.condwrite(ui.debugflag, 'hash', '%s ', hex(mf[f]))
5173 fm.condwrite(ui.debugflag, 'hash', '%s ', hex(mf[f]))
5148 fm.condwrite(ui.verbose, 'mode type', '%s %1s ', mode[fl], char[fl])
5174 fm.condwrite(ui.verbose, 'mode type', '%s %1s ', mode[fl], char[fl])
5149 fm.write('path', '%s\n', f)
5175 fm.write('path', '%s\n', f)
5150 fm.end()
5176 fm.end()
5151
5177
5152 @command('^merge',
5178 @command('^merge',
5153 [('f', 'force', None,
5179 [('f', 'force', None,
5154 _('force a merge including outstanding changes (DEPRECATED)')),
5180 _('force a merge including outstanding changes (DEPRECATED)')),
5155 ('r', 'rev', '', _('revision to merge'), _('REV')),
5181 ('r', 'rev', '', _('revision to merge'), _('REV')),
5156 ('P', 'preview', None,
5182 ('P', 'preview', None,
5157 _('review revisions to merge (no merge is performed)'))
5183 _('review revisions to merge (no merge is performed)'))
5158 ] + mergetoolopts,
5184 ] + mergetoolopts,
5159 _('[-P] [-f] [[-r] REV]'))
5185 _('[-P] [-f] [[-r] REV]'))
5160 def merge(ui, repo, node=None, **opts):
5186 def merge(ui, repo, node=None, **opts):
5161 """merge another revision into working directory
5187 """merge another revision into working directory
5162
5188
5163 The current working directory is updated with all changes made in
5189 The current working directory is updated with all changes made in
5164 the requested revision since the last common predecessor revision.
5190 the requested revision since the last common predecessor revision.
5165
5191
5166 Files that changed between either parent are marked as changed for
5192 Files that changed between either parent are marked as changed for
5167 the next commit and a commit must be performed before any further
5193 the next commit and a commit must be performed before any further
5168 updates to the repository are allowed. The next commit will have
5194 updates to the repository are allowed. The next commit will have
5169 two parents.
5195 two parents.
5170
5196
5171 ``--tool`` can be used to specify the merge tool used for file
5197 ``--tool`` can be used to specify the merge tool used for file
5172 merges. It overrides the HGMERGE environment variable and your
5198 merges. It overrides the HGMERGE environment variable and your
5173 configuration files. See :hg:`help merge-tools` for options.
5199 configuration files. See :hg:`help merge-tools` for options.
5174
5200
5175 If no revision is specified, the working directory's parent is a
5201 If no revision is specified, the working directory's parent is a
5176 head revision, and the current branch contains exactly one other
5202 head revision, and the current branch contains exactly one other
5177 head, the other head is merged with by default. Otherwise, an
5203 head, the other head is merged with by default. Otherwise, an
5178 explicit revision with which to merge with must be provided.
5204 explicit revision with which to merge with must be provided.
5179
5205
5180 See :hg:`help resolve` for information on handling file conflicts.
5206 See :hg:`help resolve` for information on handling file conflicts.
5181
5207
5182 To undo an uncommitted merge, use :hg:`update --clean .` which
5208 To undo an uncommitted merge, use :hg:`update --clean .` which
5183 will check out a clean copy of the original merge parent, losing
5209 will check out a clean copy of the original merge parent, losing
5184 all changes.
5210 all changes.
5185
5211
5186 Returns 0 on success, 1 if there are unresolved files.
5212 Returns 0 on success, 1 if there are unresolved files.
5187 """
5213 """
5188
5214
5189 if opts.get('rev') and node:
5215 if opts.get('rev') and node:
5190 raise error.Abort(_("please specify just one revision"))
5216 raise error.Abort(_("please specify just one revision"))
5191 if not node:
5217 if not node:
5192 node = opts.get('rev')
5218 node = opts.get('rev')
5193
5219
5194 if node:
5220 if node:
5195 node = scmutil.revsingle(repo, node).node()
5221 node = scmutil.revsingle(repo, node).node()
5196
5222
5197 if not node:
5223 if not node:
5198 node = repo[destutil.destmerge(repo)].node()
5224 node = repo[destutil.destmerge(repo)].node()
5199
5225
5200 if opts.get('preview'):
5226 if opts.get('preview'):
5201 # find nodes that are ancestors of p2 but not of p1
5227 # find nodes that are ancestors of p2 but not of p1
5202 p1 = repo.lookup('.')
5228 p1 = repo.lookup('.')
5203 p2 = repo.lookup(node)
5229 p2 = repo.lookup(node)
5204 nodes = repo.changelog.findmissing(common=[p1], heads=[p2])
5230 nodes = repo.changelog.findmissing(common=[p1], heads=[p2])
5205
5231
5206 displayer = cmdutil.show_changeset(ui, repo, opts)
5232 displayer = cmdutil.show_changeset(ui, repo, opts)
5207 for node in nodes:
5233 for node in nodes:
5208 displayer.show(repo[node])
5234 displayer.show(repo[node])
5209 displayer.close()
5235 displayer.close()
5210 return 0
5236 return 0
5211
5237
5212 try:
5238 try:
5213 # ui.forcemerge is an internal variable, do not document
5239 # ui.forcemerge is an internal variable, do not document
5214 repo.ui.setconfig('ui', 'forcemerge', opts.get('tool', ''), 'merge')
5240 repo.ui.setconfig('ui', 'forcemerge', opts.get('tool', ''), 'merge')
5215 return hg.merge(repo, node, force=opts.get('force'))
5241 return hg.merge(repo, node, force=opts.get('force'))
5216 finally:
5242 finally:
5217 ui.setconfig('ui', 'forcemerge', '', 'merge')
5243 ui.setconfig('ui', 'forcemerge', '', 'merge')
5218
5244
5219 @command('outgoing|out',
5245 @command('outgoing|out',
5220 [('f', 'force', None, _('run even when the destination is unrelated')),
5246 [('f', 'force', None, _('run even when the destination is unrelated')),
5221 ('r', 'rev', [],
5247 ('r', 'rev', [],
5222 _('a changeset intended to be included in the destination'), _('REV')),
5248 _('a changeset intended to be included in the destination'), _('REV')),
5223 ('n', 'newest-first', None, _('show newest record first')),
5249 ('n', 'newest-first', None, _('show newest record first')),
5224 ('B', 'bookmarks', False, _('compare bookmarks')),
5250 ('B', 'bookmarks', False, _('compare bookmarks')),
5225 ('b', 'branch', [], _('a specific branch you would like to push'),
5251 ('b', 'branch', [], _('a specific branch you would like to push'),
5226 _('BRANCH')),
5252 _('BRANCH')),
5227 ] + logopts + remoteopts + subrepoopts,
5253 ] + logopts + remoteopts + subrepoopts,
5228 _('[-M] [-p] [-n] [-f] [-r REV]... [DEST]'))
5254 _('[-M] [-p] [-n] [-f] [-r REV]... [DEST]'))
5229 def outgoing(ui, repo, dest=None, **opts):
5255 def outgoing(ui, repo, dest=None, **opts):
5230 """show changesets not found in the destination
5256 """show changesets not found in the destination
5231
5257
5232 Show changesets not found in the specified destination repository
5258 Show changesets not found in the specified destination repository
5233 or the default push location. These are the changesets that would
5259 or the default push location. These are the changesets that would
5234 be pushed if a push was requested.
5260 be pushed if a push was requested.
5235
5261
5236 See pull for details of valid destination formats.
5262 See pull for details of valid destination formats.
5237
5263
5238 .. container:: verbose
5264 .. container:: verbose
5239
5265
5240 With -B/--bookmarks, the result of bookmark comparison between
5266 With -B/--bookmarks, the result of bookmark comparison between
5241 local and remote repositories is displayed. With -v/--verbose,
5267 local and remote repositories is displayed. With -v/--verbose,
5242 status is also displayed for each bookmark like below::
5268 status is also displayed for each bookmark like below::
5243
5269
5244 BM1 01234567890a added
5270 BM1 01234567890a added
5245 BM2 deleted
5271 BM2 deleted
5246 BM3 234567890abc advanced
5272 BM3 234567890abc advanced
5247 BM4 34567890abcd diverged
5273 BM4 34567890abcd diverged
5248 BM5 4567890abcde changed
5274 BM5 4567890abcde changed
5249
5275
5250 The action taken when pushing depends on the
5276 The action taken when pushing depends on the
5251 status of each bookmark:
5277 status of each bookmark:
5252
5278
5253 :``added``: push with ``-B`` will create it
5279 :``added``: push with ``-B`` will create it
5254 :``deleted``: push with ``-B`` will delete it
5280 :``deleted``: push with ``-B`` will delete it
5255 :``advanced``: push will update it
5281 :``advanced``: push will update it
5256 :``diverged``: push with ``-B`` will update it
5282 :``diverged``: push with ``-B`` will update it
5257 :``changed``: push with ``-B`` will update it
5283 :``changed``: push with ``-B`` will update it
5258
5284
5259 From the point of view of pushing behavior, bookmarks
5285 From the point of view of pushing behavior, bookmarks
5260 existing only in the remote repository are treated as
5286 existing only in the remote repository are treated as
5261 ``deleted``, even if it is in fact added remotely.
5287 ``deleted``, even if it is in fact added remotely.
5262
5288
5263 Returns 0 if there are outgoing changes, 1 otherwise.
5289 Returns 0 if there are outgoing changes, 1 otherwise.
5264 """
5290 """
5265 if opts.get('graph'):
5291 if opts.get('graph'):
5266 cmdutil.checkunsupportedgraphflags([], opts)
5292 cmdutil.checkunsupportedgraphflags([], opts)
5267 o, other = hg._outgoing(ui, repo, dest, opts)
5293 o, other = hg._outgoing(ui, repo, dest, opts)
5268 if not o:
5294 if not o:
5269 cmdutil.outgoinghooks(ui, repo, other, opts, o)
5295 cmdutil.outgoinghooks(ui, repo, other, opts, o)
5270 return
5296 return
5271
5297
5272 revdag = cmdutil.graphrevs(repo, o, opts)
5298 revdag = cmdutil.graphrevs(repo, o, opts)
5273 displayer = cmdutil.show_changeset(ui, repo, opts, buffered=True)
5299 displayer = cmdutil.show_changeset(ui, repo, opts, buffered=True)
5274 cmdutil.displaygraph(ui, repo, revdag, displayer, graphmod.asciiedges)
5300 cmdutil.displaygraph(ui, repo, revdag, displayer, graphmod.asciiedges)
5275 cmdutil.outgoinghooks(ui, repo, other, opts, o)
5301 cmdutil.outgoinghooks(ui, repo, other, opts, o)
5276 return 0
5302 return 0
5277
5303
5278 if opts.get('bookmarks'):
5304 if opts.get('bookmarks'):
5279 dest = ui.expandpath(dest or 'default-push', dest or 'default')
5305 dest = ui.expandpath(dest or 'default-push', dest or 'default')
5280 dest, branches = hg.parseurl(dest, opts.get('branch'))
5306 dest, branches = hg.parseurl(dest, opts.get('branch'))
5281 other = hg.peer(repo, opts, dest)
5307 other = hg.peer(repo, opts, dest)
5282 if 'bookmarks' not in other.listkeys('namespaces'):
5308 if 'bookmarks' not in other.listkeys('namespaces'):
5283 ui.warn(_("remote doesn't support bookmarks\n"))
5309 ui.warn(_("remote doesn't support bookmarks\n"))
5284 return 0
5310 return 0
5285 ui.status(_('comparing with %s\n') % util.hidepassword(dest))
5311 ui.status(_('comparing with %s\n') % util.hidepassword(dest))
5286 return bookmarks.outgoing(ui, repo, other)
5312 return bookmarks.outgoing(ui, repo, other)
5287
5313
5288 repo._subtoppath = ui.expandpath(dest or 'default-push', dest or 'default')
5314 repo._subtoppath = ui.expandpath(dest or 'default-push', dest or 'default')
5289 try:
5315 try:
5290 return hg.outgoing(ui, repo, dest, opts)
5316 return hg.outgoing(ui, repo, dest, opts)
5291 finally:
5317 finally:
5292 del repo._subtoppath
5318 del repo._subtoppath
5293
5319
5294 @command('parents',
5320 @command('parents',
5295 [('r', 'rev', '', _('show parents of the specified revision'), _('REV')),
5321 [('r', 'rev', '', _('show parents of the specified revision'), _('REV')),
5296 ] + templateopts,
5322 ] + templateopts,
5297 _('[-r REV] [FILE]'),
5323 _('[-r REV] [FILE]'),
5298 inferrepo=True)
5324 inferrepo=True)
5299 def parents(ui, repo, file_=None, **opts):
5325 def parents(ui, repo, file_=None, **opts):
5300 """show the parents of the working directory or revision (DEPRECATED)
5326 """show the parents of the working directory or revision (DEPRECATED)
5301
5327
5302 Print the working directory's parent revisions. If a revision is
5328 Print the working directory's parent revisions. If a revision is
5303 given via -r/--rev, the parent of that revision will be printed.
5329 given via -r/--rev, the parent of that revision will be printed.
5304 If a file argument is given, the revision in which the file was
5330 If a file argument is given, the revision in which the file was
5305 last changed (before the working directory revision or the
5331 last changed (before the working directory revision or the
5306 argument to --rev if given) is printed.
5332 argument to --rev if given) is printed.
5307
5333
5308 This command is equivalent to::
5334 This command is equivalent to::
5309
5335
5310 hg log -r "p1()+p2()" or
5336 hg log -r "p1()+p2()" or
5311 hg log -r "p1(REV)+p2(REV)" or
5337 hg log -r "p1(REV)+p2(REV)" or
5312 hg log -r "max(::p1() and file(FILE))+max(::p2() and file(FILE))" or
5338 hg log -r "max(::p1() and file(FILE))+max(::p2() and file(FILE))" or
5313 hg log -r "max(::p1(REV) and file(FILE))+max(::p2(REV) and file(FILE))"
5339 hg log -r "max(::p1(REV) and file(FILE))+max(::p2(REV) and file(FILE))"
5314
5340
5315 See :hg:`summary` and :hg:`help revsets` for related information.
5341 See :hg:`summary` and :hg:`help revsets` for related information.
5316
5342
5317 Returns 0 on success.
5343 Returns 0 on success.
5318 """
5344 """
5319
5345
5320 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
5346 ctx = scmutil.revsingle(repo, opts.get('rev'), None)
5321
5347
5322 if file_:
5348 if file_:
5323 m = scmutil.match(ctx, (file_,), opts)
5349 m = scmutil.match(ctx, (file_,), opts)
5324 if m.anypats() or len(m.files()) != 1:
5350 if m.anypats() or len(m.files()) != 1:
5325 raise error.Abort(_('can only specify an explicit filename'))
5351 raise error.Abort(_('can only specify an explicit filename'))
5326 file_ = m.files()[0]
5352 file_ = m.files()[0]
5327 filenodes = []
5353 filenodes = []
5328 for cp in ctx.parents():
5354 for cp in ctx.parents():
5329 if not cp:
5355 if not cp:
5330 continue
5356 continue
5331 try:
5357 try:
5332 filenodes.append(cp.filenode(file_))
5358 filenodes.append(cp.filenode(file_))
5333 except error.LookupError:
5359 except error.LookupError:
5334 pass
5360 pass
5335 if not filenodes:
5361 if not filenodes:
5336 raise error.Abort(_("'%s' not found in manifest!") % file_)
5362 raise error.Abort(_("'%s' not found in manifest!") % file_)
5337 p = []
5363 p = []
5338 for fn in filenodes:
5364 for fn in filenodes:
5339 fctx = repo.filectx(file_, fileid=fn)
5365 fctx = repo.filectx(file_, fileid=fn)
5340 p.append(fctx.node())
5366 p.append(fctx.node())
5341 else:
5367 else:
5342 p = [cp.node() for cp in ctx.parents()]
5368 p = [cp.node() for cp in ctx.parents()]
5343
5369
5344 displayer = cmdutil.show_changeset(ui, repo, opts)
5370 displayer = cmdutil.show_changeset(ui, repo, opts)
5345 for n in p:
5371 for n in p:
5346 if n != nullid:
5372 if n != nullid:
5347 displayer.show(repo[n])
5373 displayer.show(repo[n])
5348 displayer.close()
5374 displayer.close()
5349
5375
5350 @command('paths', [], _('[NAME]'), optionalrepo=True)
5376 @command('paths', [], _('[NAME]'), optionalrepo=True)
5351 def paths(ui, repo, search=None):
5377 def paths(ui, repo, search=None):
5352 """show aliases for remote repositories
5378 """show aliases for remote repositories
5353
5379
5354 Show definition of symbolic path name NAME. If no name is given,
5380 Show definition of symbolic path name NAME. If no name is given,
5355 show definition of all available names.
5381 show definition of all available names.
5356
5382
5357 Option -q/--quiet suppresses all output when searching for NAME
5383 Option -q/--quiet suppresses all output when searching for NAME
5358 and shows only the path names when listing all definitions.
5384 and shows only the path names when listing all definitions.
5359
5385
5360 Path names are defined in the [paths] section of your
5386 Path names are defined in the [paths] section of your
5361 configuration file and in ``/etc/mercurial/hgrc``. If run inside a
5387 configuration file and in ``/etc/mercurial/hgrc``. If run inside a
5362 repository, ``.hg/hgrc`` is used, too.
5388 repository, ``.hg/hgrc`` is used, too.
5363
5389
5364 The path names ``default`` and ``default-push`` have a special
5390 The path names ``default`` and ``default-push`` have a special
5365 meaning. When performing a push or pull operation, they are used
5391 meaning. When performing a push or pull operation, they are used
5366 as fallbacks if no location is specified on the command-line.
5392 as fallbacks if no location is specified on the command-line.
5367 When ``default-push`` is set, it will be used for push and
5393 When ``default-push`` is set, it will be used for push and
5368 ``default`` will be used for pull; otherwise ``default`` is used
5394 ``default`` will be used for pull; otherwise ``default`` is used
5369 as the fallback for both. When cloning a repository, the clone
5395 as the fallback for both. When cloning a repository, the clone
5370 source is written as ``default`` in ``.hg/hgrc``.
5396 source is written as ``default`` in ``.hg/hgrc``.
5371
5397
5372 .. note::
5398 .. note::
5373
5399
5374 ``default`` and ``default-push`` apply to all inbound (e.g.
5400 ``default`` and ``default-push`` apply to all inbound (e.g.
5375 :hg:`incoming`) and outbound (e.g. :hg:`outgoing`, :hg:`email`
5401 :hg:`incoming`) and outbound (e.g. :hg:`outgoing`, :hg:`email`
5376 and :hg:`bundle`) operations.
5402 and :hg:`bundle`) operations.
5377
5403
5378 See :hg:`help urls` for more information.
5404 See :hg:`help urls` for more information.
5379
5405
5380 Returns 0 on success.
5406 Returns 0 on success.
5381 """
5407 """
5382 if search:
5408 if search:
5383 for name, path in sorted(ui.paths.iteritems()):
5409 for name, path in sorted(ui.paths.iteritems()):
5384 if name == search:
5410 if name == search:
5385 ui.status("%s\n" % util.hidepassword(path.rawloc))
5411 ui.status("%s\n" % util.hidepassword(path.rawloc))
5386 return
5412 return
5387 if not ui.quiet:
5413 if not ui.quiet:
5388 ui.warn(_("not found!\n"))
5414 ui.warn(_("not found!\n"))
5389 return 1
5415 return 1
5390 else:
5416 else:
5391 for name, path in sorted(ui.paths.iteritems()):
5417 for name, path in sorted(ui.paths.iteritems()):
5392 if ui.quiet:
5418 if ui.quiet:
5393 ui.write("%s\n" % name)
5419 ui.write("%s\n" % name)
5394 else:
5420 else:
5395 ui.write("%s = %s\n" % (name,
5421 ui.write("%s = %s\n" % (name,
5396 util.hidepassword(path.rawloc)))
5422 util.hidepassword(path.rawloc)))
5397 for subopt, value in sorted(path.suboptions.items()):
5423 for subopt, value in sorted(path.suboptions.items()):
5398 ui.write('%s:%s = %s\n' % (name, subopt, value))
5424 ui.write('%s:%s = %s\n' % (name, subopt, value))
5399
5425
5400 @command('phase',
5426 @command('phase',
5401 [('p', 'public', False, _('set changeset phase to public')),
5427 [('p', 'public', False, _('set changeset phase to public')),
5402 ('d', 'draft', False, _('set changeset phase to draft')),
5428 ('d', 'draft', False, _('set changeset phase to draft')),
5403 ('s', 'secret', False, _('set changeset phase to secret')),
5429 ('s', 'secret', False, _('set changeset phase to secret')),
5404 ('f', 'force', False, _('allow to move boundary backward')),
5430 ('f', 'force', False, _('allow to move boundary backward')),
5405 ('r', 'rev', [], _('target revision'), _('REV')),
5431 ('r', 'rev', [], _('target revision'), _('REV')),
5406 ],
5432 ],
5407 _('[-p|-d|-s] [-f] [-r] [REV...]'))
5433 _('[-p|-d|-s] [-f] [-r] [REV...]'))
5408 def phase(ui, repo, *revs, **opts):
5434 def phase(ui, repo, *revs, **opts):
5409 """set or show the current phase name
5435 """set or show the current phase name
5410
5436
5411 With no argument, show the phase name of the current revision(s).
5437 With no argument, show the phase name of the current revision(s).
5412
5438
5413 With one of -p/--public, -d/--draft or -s/--secret, change the
5439 With one of -p/--public, -d/--draft or -s/--secret, change the
5414 phase value of the specified revisions.
5440 phase value of the specified revisions.
5415
5441
5416 Unless -f/--force is specified, :hg:`phase` won't move changeset from a
5442 Unless -f/--force is specified, :hg:`phase` won't move changeset from a
5417 lower phase to an higher phase. Phases are ordered as follows::
5443 lower phase to an higher phase. Phases are ordered as follows::
5418
5444
5419 public < draft < secret
5445 public < draft < secret
5420
5446
5421 Returns 0 on success, 1 if some phases could not be changed.
5447 Returns 0 on success, 1 if some phases could not be changed.
5422
5448
5423 (For more information about the phases concept, see :hg:`help phases`.)
5449 (For more information about the phases concept, see :hg:`help phases`.)
5424 """
5450 """
5425 # search for a unique phase argument
5451 # search for a unique phase argument
5426 targetphase = None
5452 targetphase = None
5427 for idx, name in enumerate(phases.phasenames):
5453 for idx, name in enumerate(phases.phasenames):
5428 if opts[name]:
5454 if opts[name]:
5429 if targetphase is not None:
5455 if targetphase is not None:
5430 raise error.Abort(_('only one phase can be specified'))
5456 raise error.Abort(_('only one phase can be specified'))
5431 targetphase = idx
5457 targetphase = idx
5432
5458
5433 # look for specified revision
5459 # look for specified revision
5434 revs = list(revs)
5460 revs = list(revs)
5435 revs.extend(opts['rev'])
5461 revs.extend(opts['rev'])
5436 if not revs:
5462 if not revs:
5437 # display both parents as the second parent phase can influence
5463 # display both parents as the second parent phase can influence
5438 # the phase of a merge commit
5464 # the phase of a merge commit
5439 revs = [c.rev() for c in repo[None].parents()]
5465 revs = [c.rev() for c in repo[None].parents()]
5440
5466
5441 revs = scmutil.revrange(repo, revs)
5467 revs = scmutil.revrange(repo, revs)
5442
5468
5443 lock = None
5469 lock = None
5444 ret = 0
5470 ret = 0
5445 if targetphase is None:
5471 if targetphase is None:
5446 # display
5472 # display
5447 for r in revs:
5473 for r in revs:
5448 ctx = repo[r]
5474 ctx = repo[r]
5449 ui.write('%i: %s\n' % (ctx.rev(), ctx.phasestr()))
5475 ui.write('%i: %s\n' % (ctx.rev(), ctx.phasestr()))
5450 else:
5476 else:
5451 tr = None
5477 tr = None
5452 lock = repo.lock()
5478 lock = repo.lock()
5453 try:
5479 try:
5454 tr = repo.transaction("phase")
5480 tr = repo.transaction("phase")
5455 # set phase
5481 # set phase
5456 if not revs:
5482 if not revs:
5457 raise error.Abort(_('empty revision set'))
5483 raise error.Abort(_('empty revision set'))
5458 nodes = [repo[r].node() for r in revs]
5484 nodes = [repo[r].node() for r in revs]
5459 # moving revision from public to draft may hide them
5485 # moving revision from public to draft may hide them
5460 # We have to check result on an unfiltered repository
5486 # We have to check result on an unfiltered repository
5461 unfi = repo.unfiltered()
5487 unfi = repo.unfiltered()
5462 getphase = unfi._phasecache.phase
5488 getphase = unfi._phasecache.phase
5463 olddata = [getphase(unfi, r) for r in unfi]
5489 olddata = [getphase(unfi, r) for r in unfi]
5464 phases.advanceboundary(repo, tr, targetphase, nodes)
5490 phases.advanceboundary(repo, tr, targetphase, nodes)
5465 if opts['force']:
5491 if opts['force']:
5466 phases.retractboundary(repo, tr, targetphase, nodes)
5492 phases.retractboundary(repo, tr, targetphase, nodes)
5467 tr.close()
5493 tr.close()
5468 finally:
5494 finally:
5469 if tr is not None:
5495 if tr is not None:
5470 tr.release()
5496 tr.release()
5471 lock.release()
5497 lock.release()
5472 getphase = unfi._phasecache.phase
5498 getphase = unfi._phasecache.phase
5473 newdata = [getphase(unfi, r) for r in unfi]
5499 newdata = [getphase(unfi, r) for r in unfi]
5474 changes = sum(newdata[r] != olddata[r] for r in unfi)
5500 changes = sum(newdata[r] != olddata[r] for r in unfi)
5475 cl = unfi.changelog
5501 cl = unfi.changelog
5476 rejected = [n for n in nodes
5502 rejected = [n for n in nodes
5477 if newdata[cl.rev(n)] < targetphase]
5503 if newdata[cl.rev(n)] < targetphase]
5478 if rejected:
5504 if rejected:
5479 ui.warn(_('cannot move %i changesets to a higher '
5505 ui.warn(_('cannot move %i changesets to a higher '
5480 'phase, use --force\n') % len(rejected))
5506 'phase, use --force\n') % len(rejected))
5481 ret = 1
5507 ret = 1
5482 if changes:
5508 if changes:
5483 msg = _('phase changed for %i changesets\n') % changes
5509 msg = _('phase changed for %i changesets\n') % changes
5484 if ret:
5510 if ret:
5485 ui.status(msg)
5511 ui.status(msg)
5486 else:
5512 else:
5487 ui.note(msg)
5513 ui.note(msg)
5488 else:
5514 else:
5489 ui.warn(_('no phases changed\n'))
5515 ui.warn(_('no phases changed\n'))
5490 return ret
5516 return ret
5491
5517
5492 def postincoming(ui, repo, modheads, optupdate, checkout):
5518 def postincoming(ui, repo, modheads, optupdate, checkout):
5493 if modheads == 0:
5519 if modheads == 0:
5494 return
5520 return
5495 if optupdate:
5521 if optupdate:
5496 try:
5522 try:
5497 brev = checkout
5523 brev = checkout
5498 movemarkfrom = None
5524 movemarkfrom = None
5499 if not checkout:
5525 if not checkout:
5500 updata = destutil.destupdate(repo)
5526 updata = destutil.destupdate(repo)
5501 checkout, movemarkfrom, brev = updata
5527 checkout, movemarkfrom, brev = updata
5502 ret = hg.update(repo, checkout)
5528 ret = hg.update(repo, checkout)
5503 except error.UpdateAbort as inst:
5529 except error.UpdateAbort as inst:
5504 msg = _("not updating: %s") % str(inst)
5530 msg = _("not updating: %s") % str(inst)
5505 hint = inst.hint
5531 hint = inst.hint
5506 raise error.UpdateAbort(msg, hint=hint)
5532 raise error.UpdateAbort(msg, hint=hint)
5507 if not ret and not checkout:
5533 if not ret and not checkout:
5508 if bookmarks.update(repo, [movemarkfrom], repo['.'].node()):
5534 if bookmarks.update(repo, [movemarkfrom], repo['.'].node()):
5509 ui.status(_("updating bookmark %s\n") % repo._activebookmark)
5535 ui.status(_("updating bookmark %s\n") % repo._activebookmark)
5510 return ret
5536 return ret
5511 if modheads > 1:
5537 if modheads > 1:
5512 currentbranchheads = len(repo.branchheads())
5538 currentbranchheads = len(repo.branchheads())
5513 if currentbranchheads == modheads:
5539 if currentbranchheads == modheads:
5514 ui.status(_("(run 'hg heads' to see heads, 'hg merge' to merge)\n"))
5540 ui.status(_("(run 'hg heads' to see heads, 'hg merge' to merge)\n"))
5515 elif currentbranchheads > 1:
5541 elif currentbranchheads > 1:
5516 ui.status(_("(run 'hg heads .' to see heads, 'hg merge' to "
5542 ui.status(_("(run 'hg heads .' to see heads, 'hg merge' to "
5517 "merge)\n"))
5543 "merge)\n"))
5518 else:
5544 else:
5519 ui.status(_("(run 'hg heads' to see heads)\n"))
5545 ui.status(_("(run 'hg heads' to see heads)\n"))
5520 else:
5546 else:
5521 ui.status(_("(run 'hg update' to get a working copy)\n"))
5547 ui.status(_("(run 'hg update' to get a working copy)\n"))
5522
5548
5523 @command('^pull',
5549 @command('^pull',
5524 [('u', 'update', None,
5550 [('u', 'update', None,
5525 _('update to new branch head if changesets were pulled')),
5551 _('update to new branch head if changesets were pulled')),
5526 ('f', 'force', None, _('run even when remote repository is unrelated')),
5552 ('f', 'force', None, _('run even when remote repository is unrelated')),
5527 ('r', 'rev', [], _('a remote changeset intended to be added'), _('REV')),
5553 ('r', 'rev', [], _('a remote changeset intended to be added'), _('REV')),
5528 ('B', 'bookmark', [], _("bookmark to pull"), _('BOOKMARK')),
5554 ('B', 'bookmark', [], _("bookmark to pull"), _('BOOKMARK')),
5529 ('b', 'branch', [], _('a specific branch you would like to pull'),
5555 ('b', 'branch', [], _('a specific branch you would like to pull'),
5530 _('BRANCH')),
5556 _('BRANCH')),
5531 ] + remoteopts,
5557 ] + remoteopts,
5532 _('[-u] [-f] [-r REV]... [-e CMD] [--remotecmd CMD] [SOURCE]'))
5558 _('[-u] [-f] [-r REV]... [-e CMD] [--remotecmd CMD] [SOURCE]'))
5533 def pull(ui, repo, source="default", **opts):
5559 def pull(ui, repo, source="default", **opts):
5534 """pull changes from the specified source
5560 """pull changes from the specified source
5535
5561
5536 Pull changes from a remote repository to a local one.
5562 Pull changes from a remote repository to a local one.
5537
5563
5538 This finds all changes from the repository at the specified path
5564 This finds all changes from the repository at the specified path
5539 or URL and adds them to a local repository (the current one unless
5565 or URL and adds them to a local repository (the current one unless
5540 -R is specified). By default, this does not update the copy of the
5566 -R is specified). By default, this does not update the copy of the
5541 project in the working directory.
5567 project in the working directory.
5542
5568
5543 Use :hg:`incoming` if you want to see what would have been added
5569 Use :hg:`incoming` if you want to see what would have been added
5544 by a pull at the time you issued this command. If you then decide
5570 by a pull at the time you issued this command. If you then decide
5545 to add those changes to the repository, you should use :hg:`pull
5571 to add those changes to the repository, you should use :hg:`pull
5546 -r X` where ``X`` is the last changeset listed by :hg:`incoming`.
5572 -r X` where ``X`` is the last changeset listed by :hg:`incoming`.
5547
5573
5548 If SOURCE is omitted, the 'default' path will be used.
5574 If SOURCE is omitted, the 'default' path will be used.
5549 See :hg:`help urls` for more information.
5575 See :hg:`help urls` for more information.
5550
5576
5551 Returns 0 on success, 1 if an update had unresolved files.
5577 Returns 0 on success, 1 if an update had unresolved files.
5552 """
5578 """
5553 source, branches = hg.parseurl(ui.expandpath(source), opts.get('branch'))
5579 source, branches = hg.parseurl(ui.expandpath(source), opts.get('branch'))
5554 ui.status(_('pulling from %s\n') % util.hidepassword(source))
5580 ui.status(_('pulling from %s\n') % util.hidepassword(source))
5555 other = hg.peer(repo, opts, source)
5581 other = hg.peer(repo, opts, source)
5556 try:
5582 try:
5557 revs, checkout = hg.addbranchrevs(repo, other, branches,
5583 revs, checkout = hg.addbranchrevs(repo, other, branches,
5558 opts.get('rev'))
5584 opts.get('rev'))
5559
5585
5560
5586
5561 pullopargs = {}
5587 pullopargs = {}
5562 if opts.get('bookmark'):
5588 if opts.get('bookmark'):
5563 if not revs:
5589 if not revs:
5564 revs = []
5590 revs = []
5565 # The list of bookmark used here is not the one used to actually
5591 # The list of bookmark used here is not the one used to actually
5566 # update the bookmark name. This can result in the revision pulled
5592 # update the bookmark name. This can result in the revision pulled
5567 # not ending up with the name of the bookmark because of a race
5593 # not ending up with the name of the bookmark because of a race
5568 # condition on the server. (See issue 4689 for details)
5594 # condition on the server. (See issue 4689 for details)
5569 remotebookmarks = other.listkeys('bookmarks')
5595 remotebookmarks = other.listkeys('bookmarks')
5570 pullopargs['remotebookmarks'] = remotebookmarks
5596 pullopargs['remotebookmarks'] = remotebookmarks
5571 for b in opts['bookmark']:
5597 for b in opts['bookmark']:
5572 if b not in remotebookmarks:
5598 if b not in remotebookmarks:
5573 raise error.Abort(_('remote bookmark %s not found!') % b)
5599 raise error.Abort(_('remote bookmark %s not found!') % b)
5574 revs.append(remotebookmarks[b])
5600 revs.append(remotebookmarks[b])
5575
5601
5576 if revs:
5602 if revs:
5577 try:
5603 try:
5578 # When 'rev' is a bookmark name, we cannot guarantee that it
5604 # When 'rev' is a bookmark name, we cannot guarantee that it
5579 # will be updated with that name because of a race condition
5605 # will be updated with that name because of a race condition
5580 # server side. (See issue 4689 for details)
5606 # server side. (See issue 4689 for details)
5581 oldrevs = revs
5607 oldrevs = revs
5582 revs = [] # actually, nodes
5608 revs = [] # actually, nodes
5583 for r in oldrevs:
5609 for r in oldrevs:
5584 node = other.lookup(r)
5610 node = other.lookup(r)
5585 revs.append(node)
5611 revs.append(node)
5586 if r == checkout:
5612 if r == checkout:
5587 checkout = node
5613 checkout = node
5588 except error.CapabilityError:
5614 except error.CapabilityError:
5589 err = _("other repository doesn't support revision lookup, "
5615 err = _("other repository doesn't support revision lookup, "
5590 "so a rev cannot be specified.")
5616 "so a rev cannot be specified.")
5591 raise error.Abort(err)
5617 raise error.Abort(err)
5592
5618
5593 pullopargs.update(opts.get('opargs', {}))
5619 pullopargs.update(opts.get('opargs', {}))
5594 modheads = exchange.pull(repo, other, heads=revs,
5620 modheads = exchange.pull(repo, other, heads=revs,
5595 force=opts.get('force'),
5621 force=opts.get('force'),
5596 bookmarks=opts.get('bookmark', ()),
5622 bookmarks=opts.get('bookmark', ()),
5597 opargs=pullopargs).cgresult
5623 opargs=pullopargs).cgresult
5598 if checkout:
5624 if checkout:
5599 checkout = str(repo.changelog.rev(checkout))
5625 checkout = str(repo.changelog.rev(checkout))
5600 repo._subtoppath = source
5626 repo._subtoppath = source
5601 try:
5627 try:
5602 ret = postincoming(ui, repo, modheads, opts.get('update'), checkout)
5628 ret = postincoming(ui, repo, modheads, opts.get('update'), checkout)
5603
5629
5604 finally:
5630 finally:
5605 del repo._subtoppath
5631 del repo._subtoppath
5606
5632
5607 finally:
5633 finally:
5608 other.close()
5634 other.close()
5609 return ret
5635 return ret
5610
5636
5611 @command('^push',
5637 @command('^push',
5612 [('f', 'force', None, _('force push')),
5638 [('f', 'force', None, _('force push')),
5613 ('r', 'rev', [],
5639 ('r', 'rev', [],
5614 _('a changeset intended to be included in the destination'),
5640 _('a changeset intended to be included in the destination'),
5615 _('REV')),
5641 _('REV')),
5616 ('B', 'bookmark', [], _("bookmark to push"), _('BOOKMARK')),
5642 ('B', 'bookmark', [], _("bookmark to push"), _('BOOKMARK')),
5617 ('b', 'branch', [],
5643 ('b', 'branch', [],
5618 _('a specific branch you would like to push'), _('BRANCH')),
5644 _('a specific branch you would like to push'), _('BRANCH')),
5619 ('', 'new-branch', False, _('allow pushing a new branch')),
5645 ('', 'new-branch', False, _('allow pushing a new branch')),
5620 ] + remoteopts,
5646 ] + remoteopts,
5621 _('[-f] [-r REV]... [-e CMD] [--remotecmd CMD] [DEST]'))
5647 _('[-f] [-r REV]... [-e CMD] [--remotecmd CMD] [DEST]'))
5622 def push(ui, repo, dest=None, **opts):
5648 def push(ui, repo, dest=None, **opts):
5623 """push changes to the specified destination
5649 """push changes to the specified destination
5624
5650
5625 Push changesets from the local repository to the specified
5651 Push changesets from the local repository to the specified
5626 destination.
5652 destination.
5627
5653
5628 This operation is symmetrical to pull: it is identical to a pull
5654 This operation is symmetrical to pull: it is identical to a pull
5629 in the destination repository from the current one.
5655 in the destination repository from the current one.
5630
5656
5631 By default, push will not allow creation of new heads at the
5657 By default, push will not allow creation of new heads at the
5632 destination, since multiple heads would make it unclear which head
5658 destination, since multiple heads would make it unclear which head
5633 to use. In this situation, it is recommended to pull and merge
5659 to use. In this situation, it is recommended to pull and merge
5634 before pushing.
5660 before pushing.
5635
5661
5636 Use --new-branch if you want to allow push to create a new named
5662 Use --new-branch if you want to allow push to create a new named
5637 branch that is not present at the destination. This allows you to
5663 branch that is not present at the destination. This allows you to
5638 only create a new branch without forcing other changes.
5664 only create a new branch without forcing other changes.
5639
5665
5640 .. note::
5666 .. note::
5641
5667
5642 Extra care should be taken with the -f/--force option,
5668 Extra care should be taken with the -f/--force option,
5643 which will push all new heads on all branches, an action which will
5669 which will push all new heads on all branches, an action which will
5644 almost always cause confusion for collaborators.
5670 almost always cause confusion for collaborators.
5645
5671
5646 If -r/--rev is used, the specified revision and all its ancestors
5672 If -r/--rev is used, the specified revision and all its ancestors
5647 will be pushed to the remote repository.
5673 will be pushed to the remote repository.
5648
5674
5649 If -B/--bookmark is used, the specified bookmarked revision, its
5675 If -B/--bookmark is used, the specified bookmarked revision, its
5650 ancestors, and the bookmark will be pushed to the remote
5676 ancestors, and the bookmark will be pushed to the remote
5651 repository.
5677 repository.
5652
5678
5653 Please see :hg:`help urls` for important details about ``ssh://``
5679 Please see :hg:`help urls` for important details about ``ssh://``
5654 URLs. If DESTINATION is omitted, a default path will be used.
5680 URLs. If DESTINATION is omitted, a default path will be used.
5655
5681
5656 Returns 0 if push was successful, 1 if nothing to push.
5682 Returns 0 if push was successful, 1 if nothing to push.
5657 """
5683 """
5658
5684
5659 if opts.get('bookmark'):
5685 if opts.get('bookmark'):
5660 ui.setconfig('bookmarks', 'pushing', opts['bookmark'], 'push')
5686 ui.setconfig('bookmarks', 'pushing', opts['bookmark'], 'push')
5661 for b in opts['bookmark']:
5687 for b in opts['bookmark']:
5662 # translate -B options to -r so changesets get pushed
5688 # translate -B options to -r so changesets get pushed
5663 if b in repo._bookmarks:
5689 if b in repo._bookmarks:
5664 opts.setdefault('rev', []).append(b)
5690 opts.setdefault('rev', []).append(b)
5665 else:
5691 else:
5666 # if we try to push a deleted bookmark, translate it to null
5692 # if we try to push a deleted bookmark, translate it to null
5667 # this lets simultaneous -r, -b options continue working
5693 # this lets simultaneous -r, -b options continue working
5668 opts.setdefault('rev', []).append("null")
5694 opts.setdefault('rev', []).append("null")
5669
5695
5670 path = ui.paths.getpath(dest, default=('default-push', 'default'))
5696 path = ui.paths.getpath(dest, default=('default-push', 'default'))
5671 if not path:
5697 if not path:
5672 raise error.Abort(_('default repository not configured!'),
5698 raise error.Abort(_('default repository not configured!'),
5673 hint=_('see the "path" section in "hg help config"'))
5699 hint=_('see the "path" section in "hg help config"'))
5674 dest = path.pushloc or path.loc
5700 dest = path.pushloc or path.loc
5675 branches = (path.branch, opts.get('branch') or [])
5701 branches = (path.branch, opts.get('branch') or [])
5676 ui.status(_('pushing to %s\n') % util.hidepassword(dest))
5702 ui.status(_('pushing to %s\n') % util.hidepassword(dest))
5677 revs, checkout = hg.addbranchrevs(repo, repo, branches, opts.get('rev'))
5703 revs, checkout = hg.addbranchrevs(repo, repo, branches, opts.get('rev'))
5678 other = hg.peer(repo, opts, dest)
5704 other = hg.peer(repo, opts, dest)
5679
5705
5680 if revs:
5706 if revs:
5681 revs = [repo.lookup(r) for r in scmutil.revrange(repo, revs)]
5707 revs = [repo.lookup(r) for r in scmutil.revrange(repo, revs)]
5682 if not revs:
5708 if not revs:
5683 raise error.Abort(_("specified revisions evaluate to an empty set"),
5709 raise error.Abort(_("specified revisions evaluate to an empty set"),
5684 hint=_("use different revision arguments"))
5710 hint=_("use different revision arguments"))
5685
5711
5686 repo._subtoppath = dest
5712 repo._subtoppath = dest
5687 try:
5713 try:
5688 # push subrepos depth-first for coherent ordering
5714 # push subrepos depth-first for coherent ordering
5689 c = repo['']
5715 c = repo['']
5690 subs = c.substate # only repos that are committed
5716 subs = c.substate # only repos that are committed
5691 for s in sorted(subs):
5717 for s in sorted(subs):
5692 result = c.sub(s).push(opts)
5718 result = c.sub(s).push(opts)
5693 if result == 0:
5719 if result == 0:
5694 return not result
5720 return not result
5695 finally:
5721 finally:
5696 del repo._subtoppath
5722 del repo._subtoppath
5697 pushop = exchange.push(repo, other, opts.get('force'), revs=revs,
5723 pushop = exchange.push(repo, other, opts.get('force'), revs=revs,
5698 newbranch=opts.get('new_branch'),
5724 newbranch=opts.get('new_branch'),
5699 bookmarks=opts.get('bookmark', ()),
5725 bookmarks=opts.get('bookmark', ()),
5700 opargs=opts.get('opargs'))
5726 opargs=opts.get('opargs'))
5701
5727
5702 result = not pushop.cgresult
5728 result = not pushop.cgresult
5703
5729
5704 if pushop.bkresult is not None:
5730 if pushop.bkresult is not None:
5705 if pushop.bkresult == 2:
5731 if pushop.bkresult == 2:
5706 result = 2
5732 result = 2
5707 elif not result and pushop.bkresult:
5733 elif not result and pushop.bkresult:
5708 result = 2
5734 result = 2
5709
5735
5710 return result
5736 return result
5711
5737
5712 @command('recover', [])
5738 @command('recover', [])
5713 def recover(ui, repo):
5739 def recover(ui, repo):
5714 """roll back an interrupted transaction
5740 """roll back an interrupted transaction
5715
5741
5716 Recover from an interrupted commit or pull.
5742 Recover from an interrupted commit or pull.
5717
5743
5718 This command tries to fix the repository status after an
5744 This command tries to fix the repository status after an
5719 interrupted operation. It should only be necessary when Mercurial
5745 interrupted operation. It should only be necessary when Mercurial
5720 suggests it.
5746 suggests it.
5721
5747
5722 Returns 0 if successful, 1 if nothing to recover or verify fails.
5748 Returns 0 if successful, 1 if nothing to recover or verify fails.
5723 """
5749 """
5724 if repo.recover():
5750 if repo.recover():
5725 return hg.verify(repo)
5751 return hg.verify(repo)
5726 return 1
5752 return 1
5727
5753
5728 @command('^remove|rm',
5754 @command('^remove|rm',
5729 [('A', 'after', None, _('record delete for missing files')),
5755 [('A', 'after', None, _('record delete for missing files')),
5730 ('f', 'force', None,
5756 ('f', 'force', None,
5731 _('remove (and delete) file even if added or modified')),
5757 _('remove (and delete) file even if added or modified')),
5732 ] + subrepoopts + walkopts,
5758 ] + subrepoopts + walkopts,
5733 _('[OPTION]... FILE...'),
5759 _('[OPTION]... FILE...'),
5734 inferrepo=True)
5760 inferrepo=True)
5735 def remove(ui, repo, *pats, **opts):
5761 def remove(ui, repo, *pats, **opts):
5736 """remove the specified files on the next commit
5762 """remove the specified files on the next commit
5737
5763
5738 Schedule the indicated files for removal from the current branch.
5764 Schedule the indicated files for removal from the current branch.
5739
5765
5740 This command schedules the files to be removed at the next commit.
5766 This command schedules the files to be removed at the next commit.
5741 To undo a remove before that, see :hg:`revert`. To undo added
5767 To undo a remove before that, see :hg:`revert`. To undo added
5742 files, see :hg:`forget`.
5768 files, see :hg:`forget`.
5743
5769
5744 .. container:: verbose
5770 .. container:: verbose
5745
5771
5746 -A/--after can be used to remove only files that have already
5772 -A/--after can be used to remove only files that have already
5747 been deleted, -f/--force can be used to force deletion, and -Af
5773 been deleted, -f/--force can be used to force deletion, and -Af
5748 can be used to remove files from the next revision without
5774 can be used to remove files from the next revision without
5749 deleting them from the working directory.
5775 deleting them from the working directory.
5750
5776
5751 The following table details the behavior of remove for different
5777 The following table details the behavior of remove for different
5752 file states (columns) and option combinations (rows). The file
5778 file states (columns) and option combinations (rows). The file
5753 states are Added [A], Clean [C], Modified [M] and Missing [!]
5779 states are Added [A], Clean [C], Modified [M] and Missing [!]
5754 (as reported by :hg:`status`). The actions are Warn, Remove
5780 (as reported by :hg:`status`). The actions are Warn, Remove
5755 (from branch) and Delete (from disk):
5781 (from branch) and Delete (from disk):
5756
5782
5757 ========= == == == ==
5783 ========= == == == ==
5758 opt/state A C M !
5784 opt/state A C M !
5759 ========= == == == ==
5785 ========= == == == ==
5760 none W RD W R
5786 none W RD W R
5761 -f R RD RD R
5787 -f R RD RD R
5762 -A W W W R
5788 -A W W W R
5763 -Af R R R R
5789 -Af R R R R
5764 ========= == == == ==
5790 ========= == == == ==
5765
5791
5766 .. note::
5792 .. note::
5767
5793
5768 :hg:`remove` never deletes files in Added [A] state from the
5794 :hg:`remove` never deletes files in Added [A] state from the
5769 working directory, not even if ``--force`` is specified.
5795 working directory, not even if ``--force`` is specified.
5770
5796
5771 Returns 0 on success, 1 if any warnings encountered.
5797 Returns 0 on success, 1 if any warnings encountered.
5772 """
5798 """
5773
5799
5774 after, force = opts.get('after'), opts.get('force')
5800 after, force = opts.get('after'), opts.get('force')
5775 if not pats and not after:
5801 if not pats and not after:
5776 raise error.Abort(_('no files specified'))
5802 raise error.Abort(_('no files specified'))
5777
5803
5778 m = scmutil.match(repo[None], pats, opts)
5804 m = scmutil.match(repo[None], pats, opts)
5779 subrepos = opts.get('subrepos')
5805 subrepos = opts.get('subrepos')
5780 return cmdutil.remove(ui, repo, m, "", after, force, subrepos)
5806 return cmdutil.remove(ui, repo, m, "", after, force, subrepos)
5781
5807
5782 @command('rename|move|mv',
5808 @command('rename|move|mv',
5783 [('A', 'after', None, _('record a rename that has already occurred')),
5809 [('A', 'after', None, _('record a rename that has already occurred')),
5784 ('f', 'force', None, _('forcibly copy over an existing managed file')),
5810 ('f', 'force', None, _('forcibly copy over an existing managed file')),
5785 ] + walkopts + dryrunopts,
5811 ] + walkopts + dryrunopts,
5786 _('[OPTION]... SOURCE... DEST'))
5812 _('[OPTION]... SOURCE... DEST'))
5787 def rename(ui, repo, *pats, **opts):
5813 def rename(ui, repo, *pats, **opts):
5788 """rename files; equivalent of copy + remove
5814 """rename files; equivalent of copy + remove
5789
5815
5790 Mark dest as copies of sources; mark sources for deletion. If dest
5816 Mark dest as copies of sources; mark sources for deletion. If dest
5791 is a directory, copies are put in that directory. If dest is a
5817 is a directory, copies are put in that directory. If dest is a
5792 file, there can only be one source.
5818 file, there can only be one source.
5793
5819
5794 By default, this command copies the contents of files as they
5820 By default, this command copies the contents of files as they
5795 exist in the working directory. If invoked with -A/--after, the
5821 exist in the working directory. If invoked with -A/--after, the
5796 operation is recorded, but no copying is performed.
5822 operation is recorded, but no copying is performed.
5797
5823
5798 This command takes effect at the next commit. To undo a rename
5824 This command takes effect at the next commit. To undo a rename
5799 before that, see :hg:`revert`.
5825 before that, see :hg:`revert`.
5800
5826
5801 Returns 0 on success, 1 if errors are encountered.
5827 Returns 0 on success, 1 if errors are encountered.
5802 """
5828 """
5803 wlock = repo.wlock(False)
5829 wlock = repo.wlock(False)
5804 try:
5830 try:
5805 return cmdutil.copy(ui, repo, pats, opts, rename=True)
5831 return cmdutil.copy(ui, repo, pats, opts, rename=True)
5806 finally:
5832 finally:
5807 wlock.release()
5833 wlock.release()
5808
5834
5809 @command('resolve',
5835 @command('resolve',
5810 [('a', 'all', None, _('select all unresolved files')),
5836 [('a', 'all', None, _('select all unresolved files')),
5811 ('l', 'list', None, _('list state of files needing merge')),
5837 ('l', 'list', None, _('list state of files needing merge')),
5812 ('m', 'mark', None, _('mark files as resolved')),
5838 ('m', 'mark', None, _('mark files as resolved')),
5813 ('u', 'unmark', None, _('mark files as unresolved')),
5839 ('u', 'unmark', None, _('mark files as unresolved')),
5814 ('n', 'no-status', None, _('hide status prefix'))]
5840 ('n', 'no-status', None, _('hide status prefix'))]
5815 + mergetoolopts + walkopts + formatteropts,
5841 + mergetoolopts + walkopts + formatteropts,
5816 _('[OPTION]... [FILE]...'),
5842 _('[OPTION]... [FILE]...'),
5817 inferrepo=True)
5843 inferrepo=True)
5818 def resolve(ui, repo, *pats, **opts):
5844 def resolve(ui, repo, *pats, **opts):
5819 """redo merges or set/view the merge status of files
5845 """redo merges or set/view the merge status of files
5820
5846
5821 Merges with unresolved conflicts are often the result of
5847 Merges with unresolved conflicts are often the result of
5822 non-interactive merging using the ``internal:merge`` configuration
5848 non-interactive merging using the ``internal:merge`` configuration
5823 setting, or a command-line merge tool like ``diff3``. The resolve
5849 setting, or a command-line merge tool like ``diff3``. The resolve
5824 command is used to manage the files involved in a merge, after
5850 command is used to manage the files involved in a merge, after
5825 :hg:`merge` has been run, and before :hg:`commit` is run (i.e. the
5851 :hg:`merge` has been run, and before :hg:`commit` is run (i.e. the
5826 working directory must have two parents). See :hg:`help
5852 working directory must have two parents). See :hg:`help
5827 merge-tools` for information on configuring merge tools.
5853 merge-tools` for information on configuring merge tools.
5828
5854
5829 The resolve command can be used in the following ways:
5855 The resolve command can be used in the following ways:
5830
5856
5831 - :hg:`resolve [--tool TOOL] FILE...`: attempt to re-merge the specified
5857 - :hg:`resolve [--tool TOOL] FILE...`: attempt to re-merge the specified
5832 files, discarding any previous merge attempts. Re-merging is not
5858 files, discarding any previous merge attempts. Re-merging is not
5833 performed for files already marked as resolved. Use ``--all/-a``
5859 performed for files already marked as resolved. Use ``--all/-a``
5834 to select all unresolved files. ``--tool`` can be used to specify
5860 to select all unresolved files. ``--tool`` can be used to specify
5835 the merge tool used for the given files. It overrides the HGMERGE
5861 the merge tool used for the given files. It overrides the HGMERGE
5836 environment variable and your configuration files. Previous file
5862 environment variable and your configuration files. Previous file
5837 contents are saved with a ``.orig`` suffix.
5863 contents are saved with a ``.orig`` suffix.
5838
5864
5839 - :hg:`resolve -m [FILE]`: mark a file as having been resolved
5865 - :hg:`resolve -m [FILE]`: mark a file as having been resolved
5840 (e.g. after having manually fixed-up the files). The default is
5866 (e.g. after having manually fixed-up the files). The default is
5841 to mark all unresolved files.
5867 to mark all unresolved files.
5842
5868
5843 - :hg:`resolve -u [FILE]...`: mark a file as unresolved. The
5869 - :hg:`resolve -u [FILE]...`: mark a file as unresolved. The
5844 default is to mark all resolved files.
5870 default is to mark all resolved files.
5845
5871
5846 - :hg:`resolve -l`: list files which had or still have conflicts.
5872 - :hg:`resolve -l`: list files which had or still have conflicts.
5847 In the printed list, ``U`` = unresolved and ``R`` = resolved.
5873 In the printed list, ``U`` = unresolved and ``R`` = resolved.
5848
5874
5849 .. note::
5875 .. note::
5850
5876
5851 Mercurial will not let you commit files with unresolved merge
5877 Mercurial will not let you commit files with unresolved merge
5852 conflicts. You must use :hg:`resolve -m ...` before you can
5878 conflicts. You must use :hg:`resolve -m ...` before you can
5853 commit after a conflicting merge.
5879 commit after a conflicting merge.
5854
5880
5855 Returns 0 on success, 1 if any files fail a resolve attempt.
5881 Returns 0 on success, 1 if any files fail a resolve attempt.
5856 """
5882 """
5857
5883
5858 all, mark, unmark, show, nostatus = \
5884 all, mark, unmark, show, nostatus = \
5859 [opts.get(o) for o in 'all mark unmark list no_status'.split()]
5885 [opts.get(o) for o in 'all mark unmark list no_status'.split()]
5860
5886
5861 if (show and (mark or unmark)) or (mark and unmark):
5887 if (show and (mark or unmark)) or (mark and unmark):
5862 raise error.Abort(_("too many options specified"))
5888 raise error.Abort(_("too many options specified"))
5863 if pats and all:
5889 if pats and all:
5864 raise error.Abort(_("can't specify --all and patterns"))
5890 raise error.Abort(_("can't specify --all and patterns"))
5865 if not (all or pats or show or mark or unmark):
5891 if not (all or pats or show or mark or unmark):
5866 raise error.Abort(_('no files or directories specified'),
5892 raise error.Abort(_('no files or directories specified'),
5867 hint=('use --all to re-merge all unresolved files'))
5893 hint=('use --all to re-merge all unresolved files'))
5868
5894
5869 if show:
5895 if show:
5870 fm = ui.formatter('resolve', opts)
5896 fm = ui.formatter('resolve', opts)
5871 ms = mergemod.mergestate.read(repo)
5897 ms = mergemod.mergestate.read(repo)
5872 m = scmutil.match(repo[None], pats, opts)
5898 m = scmutil.match(repo[None], pats, opts)
5873 for f in ms:
5899 for f in ms:
5874 if not m(f):
5900 if not m(f):
5875 continue
5901 continue
5876 l = 'resolve.' + {'u': 'unresolved', 'r': 'resolved',
5902 l = 'resolve.' + {'u': 'unresolved', 'r': 'resolved',
5877 'd': 'driverresolved'}[ms[f]]
5903 'd': 'driverresolved'}[ms[f]]
5878 fm.startitem()
5904 fm.startitem()
5879 fm.condwrite(not nostatus, 'status', '%s ', ms[f].upper(), label=l)
5905 fm.condwrite(not nostatus, 'status', '%s ', ms[f].upper(), label=l)
5880 fm.write('path', '%s\n', f, label=l)
5906 fm.write('path', '%s\n', f, label=l)
5881 fm.end()
5907 fm.end()
5882 return 0
5908 return 0
5883
5909
5884 wlock = repo.wlock()
5910 wlock = repo.wlock()
5885 try:
5911 try:
5886 ms = mergemod.mergestate.read(repo)
5912 ms = mergemod.mergestate.read(repo)
5887
5913
5888 if not (ms.active() or repo.dirstate.p2() != nullid):
5914 if not (ms.active() or repo.dirstate.p2() != nullid):
5889 raise error.Abort(
5915 raise error.Abort(
5890 _('resolve command not applicable when not merging'))
5916 _('resolve command not applicable when not merging'))
5891
5917
5892 wctx = repo[None]
5918 wctx = repo[None]
5893
5919
5894 if ms.mergedriver and ms.mdstate() == 'u':
5920 if ms.mergedriver and ms.mdstate() == 'u':
5895 proceed = mergemod.driverpreprocess(repo, ms, wctx)
5921 proceed = mergemod.driverpreprocess(repo, ms, wctx)
5896 ms.commit()
5922 ms.commit()
5897 # allow mark and unmark to go through
5923 # allow mark and unmark to go through
5898 if not mark and not unmark and not proceed:
5924 if not mark and not unmark and not proceed:
5899 return 1
5925 return 1
5900
5926
5901 m = scmutil.match(wctx, pats, opts)
5927 m = scmutil.match(wctx, pats, opts)
5902 ret = 0
5928 ret = 0
5903 didwork = False
5929 didwork = False
5904 runconclude = False
5930 runconclude = False
5905
5931
5906 tocomplete = []
5932 tocomplete = []
5907 for f in ms:
5933 for f in ms:
5908 if not m(f):
5934 if not m(f):
5909 continue
5935 continue
5910
5936
5911 didwork = True
5937 didwork = True
5912
5938
5913 # don't let driver-resolved files be marked, and run the conclude
5939 # don't let driver-resolved files be marked, and run the conclude
5914 # step if asked to resolve
5940 # step if asked to resolve
5915 if ms[f] == "d":
5941 if ms[f] == "d":
5916 exact = m.exact(f)
5942 exact = m.exact(f)
5917 if mark:
5943 if mark:
5918 if exact:
5944 if exact:
5919 ui.warn(_('not marking %s as it is driver-resolved\n')
5945 ui.warn(_('not marking %s as it is driver-resolved\n')
5920 % f)
5946 % f)
5921 elif unmark:
5947 elif unmark:
5922 if exact:
5948 if exact:
5923 ui.warn(_('not unmarking %s as it is driver-resolved\n')
5949 ui.warn(_('not unmarking %s as it is driver-resolved\n')
5924 % f)
5950 % f)
5925 else:
5951 else:
5926 runconclude = True
5952 runconclude = True
5927 continue
5953 continue
5928
5954
5929 if mark:
5955 if mark:
5930 ms.mark(f, "r")
5956 ms.mark(f, "r")
5931 elif unmark:
5957 elif unmark:
5932 ms.mark(f, "u")
5958 ms.mark(f, "u")
5933 else:
5959 else:
5934 # backup pre-resolve (merge uses .orig for its own purposes)
5960 # backup pre-resolve (merge uses .orig for its own purposes)
5935 a = repo.wjoin(f)
5961 a = repo.wjoin(f)
5936 try:
5962 try:
5937 util.copyfile(a, a + ".resolve")
5963 util.copyfile(a, a + ".resolve")
5938 except (IOError, OSError) as inst:
5964 except (IOError, OSError) as inst:
5939 if inst.errno != errno.ENOENT:
5965 if inst.errno != errno.ENOENT:
5940 raise
5966 raise
5941
5967
5942 try:
5968 try:
5943 # preresolve file
5969 # preresolve file
5944 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
5970 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
5945 'resolve')
5971 'resolve')
5946 complete, r = ms.preresolve(f, wctx)
5972 complete, r = ms.preresolve(f, wctx)
5947 if not complete:
5973 if not complete:
5948 tocomplete.append(f)
5974 tocomplete.append(f)
5949 elif r:
5975 elif r:
5950 ret = 1
5976 ret = 1
5951 finally:
5977 finally:
5952 ui.setconfig('ui', 'forcemerge', '', 'resolve')
5978 ui.setconfig('ui', 'forcemerge', '', 'resolve')
5953 ms.commit()
5979 ms.commit()
5954
5980
5955 # replace filemerge's .orig file with our resolve file, but only
5981 # replace filemerge's .orig file with our resolve file, but only
5956 # for merges that are complete
5982 # for merges that are complete
5957 if complete:
5983 if complete:
5958 try:
5984 try:
5959 util.rename(a + ".resolve",
5985 util.rename(a + ".resolve",
5960 scmutil.origpath(ui, repo, a))
5986 scmutil.origpath(ui, repo, a))
5961 except OSError as inst:
5987 except OSError as inst:
5962 if inst.errno != errno.ENOENT:
5988 if inst.errno != errno.ENOENT:
5963 raise
5989 raise
5964
5990
5965 for f in tocomplete:
5991 for f in tocomplete:
5966 try:
5992 try:
5967 # resolve file
5993 # resolve file
5968 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
5994 ui.setconfig('ui', 'forcemerge', opts.get('tool', ''),
5969 'resolve')
5995 'resolve')
5970 r = ms.resolve(f, wctx)
5996 r = ms.resolve(f, wctx)
5971 if r:
5997 if r:
5972 ret = 1
5998 ret = 1
5973 finally:
5999 finally:
5974 ui.setconfig('ui', 'forcemerge', '', 'resolve')
6000 ui.setconfig('ui', 'forcemerge', '', 'resolve')
5975 ms.commit()
6001 ms.commit()
5976
6002
5977 # replace filemerge's .orig file with our resolve file
6003 # replace filemerge's .orig file with our resolve file
5978 a = repo.wjoin(f)
6004 a = repo.wjoin(f)
5979 try:
6005 try:
5980 util.rename(a + ".resolve", scmutil.origpath(ui, repo, a))
6006 util.rename(a + ".resolve", scmutil.origpath(ui, repo, a))
5981 except OSError as inst:
6007 except OSError as inst:
5982 if inst.errno != errno.ENOENT:
6008 if inst.errno != errno.ENOENT:
5983 raise
6009 raise
5984
6010
5985 ms.commit()
6011 ms.commit()
5986 ms.recordactions()
6012 ms.recordactions()
5987
6013
5988 if not didwork and pats:
6014 if not didwork and pats:
5989 ui.warn(_("arguments do not match paths that need resolving\n"))
6015 ui.warn(_("arguments do not match paths that need resolving\n"))
5990 elif ms.mergedriver and ms.mdstate() != 's':
6016 elif ms.mergedriver and ms.mdstate() != 's':
5991 # run conclude step when either a driver-resolved file is requested
6017 # run conclude step when either a driver-resolved file is requested
5992 # or there are no driver-resolved files
6018 # or there are no driver-resolved files
5993 # we can't use 'ret' to determine whether any files are unresolved
6019 # we can't use 'ret' to determine whether any files are unresolved
5994 # because we might not have tried to resolve some
6020 # because we might not have tried to resolve some
5995 if ((runconclude or not list(ms.driverresolved()))
6021 if ((runconclude or not list(ms.driverresolved()))
5996 and not list(ms.unresolved())):
6022 and not list(ms.unresolved())):
5997 proceed = mergemod.driverconclude(repo, ms, wctx)
6023 proceed = mergemod.driverconclude(repo, ms, wctx)
5998 ms.commit()
6024 ms.commit()
5999 if not proceed:
6025 if not proceed:
6000 return 1
6026 return 1
6001
6027
6002 finally:
6028 finally:
6003 wlock.release()
6029 wlock.release()
6004
6030
6005 # Nudge users into finishing an unfinished operation
6031 # Nudge users into finishing an unfinished operation
6006 unresolvedf = list(ms.unresolved())
6032 unresolvedf = list(ms.unresolved())
6007 driverresolvedf = list(ms.driverresolved())
6033 driverresolvedf = list(ms.driverresolved())
6008 if not unresolvedf and not driverresolvedf:
6034 if not unresolvedf and not driverresolvedf:
6009 ui.status(_('(no more unresolved files)\n'))
6035 ui.status(_('(no more unresolved files)\n'))
6010 cmdutil.checkafterresolved(repo)
6036 cmdutil.checkafterresolved(repo)
6011 elif not unresolvedf:
6037 elif not unresolvedf:
6012 ui.status(_('(no more unresolved files -- '
6038 ui.status(_('(no more unresolved files -- '
6013 'run "hg resolve --all" to conclude)\n'))
6039 'run "hg resolve --all" to conclude)\n'))
6014
6040
6015 return ret
6041 return ret
6016
6042
6017 @command('revert',
6043 @command('revert',
6018 [('a', 'all', None, _('revert all changes when no arguments given')),
6044 [('a', 'all', None, _('revert all changes when no arguments given')),
6019 ('d', 'date', '', _('tipmost revision matching date'), _('DATE')),
6045 ('d', 'date', '', _('tipmost revision matching date'), _('DATE')),
6020 ('r', 'rev', '', _('revert to the specified revision'), _('REV')),
6046 ('r', 'rev', '', _('revert to the specified revision'), _('REV')),
6021 ('C', 'no-backup', None, _('do not save backup copies of files')),
6047 ('C', 'no-backup', None, _('do not save backup copies of files')),
6022 ('i', 'interactive', None,
6048 ('i', 'interactive', None,
6023 _('interactively select the changes (EXPERIMENTAL)')),
6049 _('interactively select the changes (EXPERIMENTAL)')),
6024 ] + walkopts + dryrunopts,
6050 ] + walkopts + dryrunopts,
6025 _('[OPTION]... [-r REV] [NAME]...'))
6051 _('[OPTION]... [-r REV] [NAME]...'))
6026 def revert(ui, repo, *pats, **opts):
6052 def revert(ui, repo, *pats, **opts):
6027 """restore files to their checkout state
6053 """restore files to their checkout state
6028
6054
6029 .. note::
6055 .. note::
6030
6056
6031 To check out earlier revisions, you should use :hg:`update REV`.
6057 To check out earlier revisions, you should use :hg:`update REV`.
6032 To cancel an uncommitted merge (and lose your changes),
6058 To cancel an uncommitted merge (and lose your changes),
6033 use :hg:`update --clean .`.
6059 use :hg:`update --clean .`.
6034
6060
6035 With no revision specified, revert the specified files or directories
6061 With no revision specified, revert the specified files or directories
6036 to the contents they had in the parent of the working directory.
6062 to the contents they had in the parent of the working directory.
6037 This restores the contents of files to an unmodified
6063 This restores the contents of files to an unmodified
6038 state and unschedules adds, removes, copies, and renames. If the
6064 state and unschedules adds, removes, copies, and renames. If the
6039 working directory has two parents, you must explicitly specify a
6065 working directory has two parents, you must explicitly specify a
6040 revision.
6066 revision.
6041
6067
6042 Using the -r/--rev or -d/--date options, revert the given files or
6068 Using the -r/--rev or -d/--date options, revert the given files or
6043 directories to their states as of a specific revision. Because
6069 directories to their states as of a specific revision. Because
6044 revert does not change the working directory parents, this will
6070 revert does not change the working directory parents, this will
6045 cause these files to appear modified. This can be helpful to "back
6071 cause these files to appear modified. This can be helpful to "back
6046 out" some or all of an earlier change. See :hg:`backout` for a
6072 out" some or all of an earlier change. See :hg:`backout` for a
6047 related method.
6073 related method.
6048
6074
6049 Modified files are saved with a .orig suffix before reverting.
6075 Modified files are saved with a .orig suffix before reverting.
6050 To disable these backups, use --no-backup.
6076 To disable these backups, use --no-backup.
6051
6077
6052 See :hg:`help dates` for a list of formats valid for -d/--date.
6078 See :hg:`help dates` for a list of formats valid for -d/--date.
6053
6079
6054 See :hg:`help backout` for a way to reverse the effect of an
6080 See :hg:`help backout` for a way to reverse the effect of an
6055 earlier changeset.
6081 earlier changeset.
6056
6082
6057 Returns 0 on success.
6083 Returns 0 on success.
6058 """
6084 """
6059
6085
6060 if opts.get("date"):
6086 if opts.get("date"):
6061 if opts.get("rev"):
6087 if opts.get("rev"):
6062 raise error.Abort(_("you can't specify a revision and a date"))
6088 raise error.Abort(_("you can't specify a revision and a date"))
6063 opts["rev"] = cmdutil.finddate(ui, repo, opts["date"])
6089 opts["rev"] = cmdutil.finddate(ui, repo, opts["date"])
6064
6090
6065 parent, p2 = repo.dirstate.parents()
6091 parent, p2 = repo.dirstate.parents()
6066 if not opts.get('rev') and p2 != nullid:
6092 if not opts.get('rev') and p2 != nullid:
6067 # revert after merge is a trap for new users (issue2915)
6093 # revert after merge is a trap for new users (issue2915)
6068 raise error.Abort(_('uncommitted merge with no revision specified'),
6094 raise error.Abort(_('uncommitted merge with no revision specified'),
6069 hint=_('use "hg update" or see "hg help revert"'))
6095 hint=_('use "hg update" or see "hg help revert"'))
6070
6096
6071 ctx = scmutil.revsingle(repo, opts.get('rev'))
6097 ctx = scmutil.revsingle(repo, opts.get('rev'))
6072
6098
6073 if (not (pats or opts.get('include') or opts.get('exclude') or
6099 if (not (pats or opts.get('include') or opts.get('exclude') or
6074 opts.get('all') or opts.get('interactive'))):
6100 opts.get('all') or opts.get('interactive'))):
6075 msg = _("no files or directories specified")
6101 msg = _("no files or directories specified")
6076 if p2 != nullid:
6102 if p2 != nullid:
6077 hint = _("uncommitted merge, use --all to discard all changes,"
6103 hint = _("uncommitted merge, use --all to discard all changes,"
6078 " or 'hg update -C .' to abort the merge")
6104 " or 'hg update -C .' to abort the merge")
6079 raise error.Abort(msg, hint=hint)
6105 raise error.Abort(msg, hint=hint)
6080 dirty = any(repo.status())
6106 dirty = any(repo.status())
6081 node = ctx.node()
6107 node = ctx.node()
6082 if node != parent:
6108 if node != parent:
6083 if dirty:
6109 if dirty:
6084 hint = _("uncommitted changes, use --all to discard all"
6110 hint = _("uncommitted changes, use --all to discard all"
6085 " changes, or 'hg update %s' to update") % ctx.rev()
6111 " changes, or 'hg update %s' to update") % ctx.rev()
6086 else:
6112 else:
6087 hint = _("use --all to revert all files,"
6113 hint = _("use --all to revert all files,"
6088 " or 'hg update %s' to update") % ctx.rev()
6114 " or 'hg update %s' to update") % ctx.rev()
6089 elif dirty:
6115 elif dirty:
6090 hint = _("uncommitted changes, use --all to discard all changes")
6116 hint = _("uncommitted changes, use --all to discard all changes")
6091 else:
6117 else:
6092 hint = _("use --all to revert all files")
6118 hint = _("use --all to revert all files")
6093 raise error.Abort(msg, hint=hint)
6119 raise error.Abort(msg, hint=hint)
6094
6120
6095 return cmdutil.revert(ui, repo, ctx, (parent, p2), *pats, **opts)
6121 return cmdutil.revert(ui, repo, ctx, (parent, p2), *pats, **opts)
6096
6122
6097 @command('rollback', dryrunopts +
6123 @command('rollback', dryrunopts +
6098 [('f', 'force', False, _('ignore safety measures'))])
6124 [('f', 'force', False, _('ignore safety measures'))])
6099 def rollback(ui, repo, **opts):
6125 def rollback(ui, repo, **opts):
6100 """roll back the last transaction (DANGEROUS) (DEPRECATED)
6126 """roll back the last transaction (DANGEROUS) (DEPRECATED)
6101
6127
6102 Please use :hg:`commit --amend` instead of rollback to correct
6128 Please use :hg:`commit --amend` instead of rollback to correct
6103 mistakes in the last commit.
6129 mistakes in the last commit.
6104
6130
6105 This command should be used with care. There is only one level of
6131 This command should be used with care. There is only one level of
6106 rollback, and there is no way to undo a rollback. It will also
6132 rollback, and there is no way to undo a rollback. It will also
6107 restore the dirstate at the time of the last transaction, losing
6133 restore the dirstate at the time of the last transaction, losing
6108 any dirstate changes since that time. This command does not alter
6134 any dirstate changes since that time. This command does not alter
6109 the working directory.
6135 the working directory.
6110
6136
6111 Transactions are used to encapsulate the effects of all commands
6137 Transactions are used to encapsulate the effects of all commands
6112 that create new changesets or propagate existing changesets into a
6138 that create new changesets or propagate existing changesets into a
6113 repository.
6139 repository.
6114
6140
6115 .. container:: verbose
6141 .. container:: verbose
6116
6142
6117 For example, the following commands are transactional, and their
6143 For example, the following commands are transactional, and their
6118 effects can be rolled back:
6144 effects can be rolled back:
6119
6145
6120 - commit
6146 - commit
6121 - import
6147 - import
6122 - pull
6148 - pull
6123 - push (with this repository as the destination)
6149 - push (with this repository as the destination)
6124 - unbundle
6150 - unbundle
6125
6151
6126 To avoid permanent data loss, rollback will refuse to rollback a
6152 To avoid permanent data loss, rollback will refuse to rollback a
6127 commit transaction if it isn't checked out. Use --force to
6153 commit transaction if it isn't checked out. Use --force to
6128 override this protection.
6154 override this protection.
6129
6155
6130 This command is not intended for use on public repositories. Once
6156 This command is not intended for use on public repositories. Once
6131 changes are visible for pull by other users, rolling a transaction
6157 changes are visible for pull by other users, rolling a transaction
6132 back locally is ineffective (someone else may already have pulled
6158 back locally is ineffective (someone else may already have pulled
6133 the changes). Furthermore, a race is possible with readers of the
6159 the changes). Furthermore, a race is possible with readers of the
6134 repository; for example an in-progress pull from the repository
6160 repository; for example an in-progress pull from the repository
6135 may fail if a rollback is performed.
6161 may fail if a rollback is performed.
6136
6162
6137 Returns 0 on success, 1 if no rollback data is available.
6163 Returns 0 on success, 1 if no rollback data is available.
6138 """
6164 """
6139 return repo.rollback(dryrun=opts.get('dry_run'),
6165 return repo.rollback(dryrun=opts.get('dry_run'),
6140 force=opts.get('force'))
6166 force=opts.get('force'))
6141
6167
6142 @command('root', [])
6168 @command('root', [])
6143 def root(ui, repo):
6169 def root(ui, repo):
6144 """print the root (top) of the current working directory
6170 """print the root (top) of the current working directory
6145
6171
6146 Print the root directory of the current repository.
6172 Print the root directory of the current repository.
6147
6173
6148 Returns 0 on success.
6174 Returns 0 on success.
6149 """
6175 """
6150 ui.write(repo.root + "\n")
6176 ui.write(repo.root + "\n")
6151
6177
6152 @command('^serve',
6178 @command('^serve',
6153 [('A', 'accesslog', '', _('name of access log file to write to'),
6179 [('A', 'accesslog', '', _('name of access log file to write to'),
6154 _('FILE')),
6180 _('FILE')),
6155 ('d', 'daemon', None, _('run server in background')),
6181 ('d', 'daemon', None, _('run server in background')),
6156 ('', 'daemon-pipefds', '', _('used internally by daemon mode'), _('FILE')),
6182 ('', 'daemon-pipefds', '', _('used internally by daemon mode'), _('FILE')),
6157 ('E', 'errorlog', '', _('name of error log file to write to'), _('FILE')),
6183 ('E', 'errorlog', '', _('name of error log file to write to'), _('FILE')),
6158 # use string type, then we can check if something was passed
6184 # use string type, then we can check if something was passed
6159 ('p', 'port', '', _('port to listen on (default: 8000)'), _('PORT')),
6185 ('p', 'port', '', _('port to listen on (default: 8000)'), _('PORT')),
6160 ('a', 'address', '', _('address to listen on (default: all interfaces)'),
6186 ('a', 'address', '', _('address to listen on (default: all interfaces)'),
6161 _('ADDR')),
6187 _('ADDR')),
6162 ('', 'prefix', '', _('prefix path to serve from (default: server root)'),
6188 ('', 'prefix', '', _('prefix path to serve from (default: server root)'),
6163 _('PREFIX')),
6189 _('PREFIX')),
6164 ('n', 'name', '',
6190 ('n', 'name', '',
6165 _('name to show in web pages (default: working directory)'), _('NAME')),
6191 _('name to show in web pages (default: working directory)'), _('NAME')),
6166 ('', 'web-conf', '',
6192 ('', 'web-conf', '',
6167 _('name of the hgweb config file (see "hg help hgweb")'), _('FILE')),
6193 _('name of the hgweb config file (see "hg help hgweb")'), _('FILE')),
6168 ('', 'webdir-conf', '', _('name of the hgweb config file (DEPRECATED)'),
6194 ('', 'webdir-conf', '', _('name of the hgweb config file (DEPRECATED)'),
6169 _('FILE')),
6195 _('FILE')),
6170 ('', 'pid-file', '', _('name of file to write process ID to'), _('FILE')),
6196 ('', 'pid-file', '', _('name of file to write process ID to'), _('FILE')),
6171 ('', 'stdio', None, _('for remote clients')),
6197 ('', 'stdio', None, _('for remote clients')),
6172 ('', 'cmdserver', '', _('for remote clients'), _('MODE')),
6198 ('', 'cmdserver', '', _('for remote clients'), _('MODE')),
6173 ('t', 'templates', '', _('web templates to use'), _('TEMPLATE')),
6199 ('t', 'templates', '', _('web templates to use'), _('TEMPLATE')),
6174 ('', 'style', '', _('template style to use'), _('STYLE')),
6200 ('', 'style', '', _('template style to use'), _('STYLE')),
6175 ('6', 'ipv6', None, _('use IPv6 in addition to IPv4')),
6201 ('6', 'ipv6', None, _('use IPv6 in addition to IPv4')),
6176 ('', 'certificate', '', _('SSL certificate file'), _('FILE'))],
6202 ('', 'certificate', '', _('SSL certificate file'), _('FILE'))],
6177 _('[OPTION]...'),
6203 _('[OPTION]...'),
6178 optionalrepo=True)
6204 optionalrepo=True)
6179 def serve(ui, repo, **opts):
6205 def serve(ui, repo, **opts):
6180 """start stand-alone webserver
6206 """start stand-alone webserver
6181
6207
6182 Start a local HTTP repository browser and pull server. You can use
6208 Start a local HTTP repository browser and pull server. You can use
6183 this for ad-hoc sharing and browsing of repositories. It is
6209 this for ad-hoc sharing and browsing of repositories. It is
6184 recommended to use a real web server to serve a repository for
6210 recommended to use a real web server to serve a repository for
6185 longer periods of time.
6211 longer periods of time.
6186
6212
6187 Please note that the server does not implement access control.
6213 Please note that the server does not implement access control.
6188 This means that, by default, anybody can read from the server and
6214 This means that, by default, anybody can read from the server and
6189 nobody can write to it by default. Set the ``web.allow_push``
6215 nobody can write to it by default. Set the ``web.allow_push``
6190 option to ``*`` to allow everybody to push to the server. You
6216 option to ``*`` to allow everybody to push to the server. You
6191 should use a real web server if you need to authenticate users.
6217 should use a real web server if you need to authenticate users.
6192
6218
6193 By default, the server logs accesses to stdout and errors to
6219 By default, the server logs accesses to stdout and errors to
6194 stderr. Use the -A/--accesslog and -E/--errorlog options to log to
6220 stderr. Use the -A/--accesslog and -E/--errorlog options to log to
6195 files.
6221 files.
6196
6222
6197 To have the server choose a free port number to listen on, specify
6223 To have the server choose a free port number to listen on, specify
6198 a port number of 0; in this case, the server will print the port
6224 a port number of 0; in this case, the server will print the port
6199 number it uses.
6225 number it uses.
6200
6226
6201 Returns 0 on success.
6227 Returns 0 on success.
6202 """
6228 """
6203
6229
6204 if opts["stdio"] and opts["cmdserver"]:
6230 if opts["stdio"] and opts["cmdserver"]:
6205 raise error.Abort(_("cannot use --stdio with --cmdserver"))
6231 raise error.Abort(_("cannot use --stdio with --cmdserver"))
6206
6232
6207 if opts["stdio"]:
6233 if opts["stdio"]:
6208 if repo is None:
6234 if repo is None:
6209 raise error.RepoError(_("there is no Mercurial repository here"
6235 raise error.RepoError(_("there is no Mercurial repository here"
6210 " (.hg not found)"))
6236 " (.hg not found)"))
6211 s = sshserver.sshserver(ui, repo)
6237 s = sshserver.sshserver(ui, repo)
6212 s.serve_forever()
6238 s.serve_forever()
6213
6239
6214 if opts["cmdserver"]:
6240 if opts["cmdserver"]:
6215 service = commandserver.createservice(ui, repo, opts)
6241 service = commandserver.createservice(ui, repo, opts)
6216 else:
6242 else:
6217 service = hgweb.createservice(ui, repo, opts)
6243 service = hgweb.createservice(ui, repo, opts)
6218 return cmdutil.service(opts, initfn=service.init, runfn=service.run)
6244 return cmdutil.service(opts, initfn=service.init, runfn=service.run)
6219
6245
6220 @command('^status|st',
6246 @command('^status|st',
6221 [('A', 'all', None, _('show status of all files')),
6247 [('A', 'all', None, _('show status of all files')),
6222 ('m', 'modified', None, _('show only modified files')),
6248 ('m', 'modified', None, _('show only modified files')),
6223 ('a', 'added', None, _('show only added files')),
6249 ('a', 'added', None, _('show only added files')),
6224 ('r', 'removed', None, _('show only removed files')),
6250 ('r', 'removed', None, _('show only removed files')),
6225 ('d', 'deleted', None, _('show only deleted (but tracked) files')),
6251 ('d', 'deleted', None, _('show only deleted (but tracked) files')),
6226 ('c', 'clean', None, _('show only files without changes')),
6252 ('c', 'clean', None, _('show only files without changes')),
6227 ('u', 'unknown', None, _('show only unknown (not tracked) files')),
6253 ('u', 'unknown', None, _('show only unknown (not tracked) files')),
6228 ('i', 'ignored', None, _('show only ignored files')),
6254 ('i', 'ignored', None, _('show only ignored files')),
6229 ('n', 'no-status', None, _('hide status prefix')),
6255 ('n', 'no-status', None, _('hide status prefix')),
6230 ('C', 'copies', None, _('show source of copied files')),
6256 ('C', 'copies', None, _('show source of copied files')),
6231 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
6257 ('0', 'print0', None, _('end filenames with NUL, for use with xargs')),
6232 ('', 'rev', [], _('show difference from revision'), _('REV')),
6258 ('', 'rev', [], _('show difference from revision'), _('REV')),
6233 ('', 'change', '', _('list the changed files of a revision'), _('REV')),
6259 ('', 'change', '', _('list the changed files of a revision'), _('REV')),
6234 ] + walkopts + subrepoopts + formatteropts,
6260 ] + walkopts + subrepoopts + formatteropts,
6235 _('[OPTION]... [FILE]...'),
6261 _('[OPTION]... [FILE]...'),
6236 inferrepo=True)
6262 inferrepo=True)
6237 def status(ui, repo, *pats, **opts):
6263 def status(ui, repo, *pats, **opts):
6238 """show changed files in the working directory
6264 """show changed files in the working directory
6239
6265
6240 Show status of files in the repository. If names are given, only
6266 Show status of files in the repository. If names are given, only
6241 files that match are shown. Files that are clean or ignored or
6267 files that match are shown. Files that are clean or ignored or
6242 the source of a copy/move operation, are not listed unless
6268 the source of a copy/move operation, are not listed unless
6243 -c/--clean, -i/--ignored, -C/--copies or -A/--all are given.
6269 -c/--clean, -i/--ignored, -C/--copies or -A/--all are given.
6244 Unless options described with "show only ..." are given, the
6270 Unless options described with "show only ..." are given, the
6245 options -mardu are used.
6271 options -mardu are used.
6246
6272
6247 Option -q/--quiet hides untracked (unknown and ignored) files
6273 Option -q/--quiet hides untracked (unknown and ignored) files
6248 unless explicitly requested with -u/--unknown or -i/--ignored.
6274 unless explicitly requested with -u/--unknown or -i/--ignored.
6249
6275
6250 .. note::
6276 .. note::
6251
6277
6252 :hg:`status` may appear to disagree with diff if permissions have
6278 :hg:`status` may appear to disagree with diff if permissions have
6253 changed or a merge has occurred. The standard diff format does
6279 changed or a merge has occurred. The standard diff format does
6254 not report permission changes and diff only reports changes
6280 not report permission changes and diff only reports changes
6255 relative to one merge parent.
6281 relative to one merge parent.
6256
6282
6257 If one revision is given, it is used as the base revision.
6283 If one revision is given, it is used as the base revision.
6258 If two revisions are given, the differences between them are
6284 If two revisions are given, the differences between them are
6259 shown. The --change option can also be used as a shortcut to list
6285 shown. The --change option can also be used as a shortcut to list
6260 the changed files of a revision from its first parent.
6286 the changed files of a revision from its first parent.
6261
6287
6262 The codes used to show the status of files are::
6288 The codes used to show the status of files are::
6263
6289
6264 M = modified
6290 M = modified
6265 A = added
6291 A = added
6266 R = removed
6292 R = removed
6267 C = clean
6293 C = clean
6268 ! = missing (deleted by non-hg command, but still tracked)
6294 ! = missing (deleted by non-hg command, but still tracked)
6269 ? = not tracked
6295 ? = not tracked
6270 I = ignored
6296 I = ignored
6271 = origin of the previous file (with --copies)
6297 = origin of the previous file (with --copies)
6272
6298
6273 .. container:: verbose
6299 .. container:: verbose
6274
6300
6275 Examples:
6301 Examples:
6276
6302
6277 - show changes in the working directory relative to a
6303 - show changes in the working directory relative to a
6278 changeset::
6304 changeset::
6279
6305
6280 hg status --rev 9353
6306 hg status --rev 9353
6281
6307
6282 - show changes in the working directory relative to the
6308 - show changes in the working directory relative to the
6283 current directory (see :hg:`help patterns` for more information)::
6309 current directory (see :hg:`help patterns` for more information)::
6284
6310
6285 hg status re:
6311 hg status re:
6286
6312
6287 - show all changes including copies in an existing changeset::
6313 - show all changes including copies in an existing changeset::
6288
6314
6289 hg status --copies --change 9353
6315 hg status --copies --change 9353
6290
6316
6291 - get a NUL separated list of added files, suitable for xargs::
6317 - get a NUL separated list of added files, suitable for xargs::
6292
6318
6293 hg status -an0
6319 hg status -an0
6294
6320
6295 Returns 0 on success.
6321 Returns 0 on success.
6296 """
6322 """
6297
6323
6298 revs = opts.get('rev')
6324 revs = opts.get('rev')
6299 change = opts.get('change')
6325 change = opts.get('change')
6300
6326
6301 if revs and change:
6327 if revs and change:
6302 msg = _('cannot specify --rev and --change at the same time')
6328 msg = _('cannot specify --rev and --change at the same time')
6303 raise error.Abort(msg)
6329 raise error.Abort(msg)
6304 elif change:
6330 elif change:
6305 node2 = scmutil.revsingle(repo, change, None).node()
6331 node2 = scmutil.revsingle(repo, change, None).node()
6306 node1 = repo[node2].p1().node()
6332 node1 = repo[node2].p1().node()
6307 else:
6333 else:
6308 node1, node2 = scmutil.revpair(repo, revs)
6334 node1, node2 = scmutil.revpair(repo, revs)
6309
6335
6310 if pats:
6336 if pats:
6311 cwd = repo.getcwd()
6337 cwd = repo.getcwd()
6312 else:
6338 else:
6313 cwd = ''
6339 cwd = ''
6314
6340
6315 if opts.get('print0'):
6341 if opts.get('print0'):
6316 end = '\0'
6342 end = '\0'
6317 else:
6343 else:
6318 end = '\n'
6344 end = '\n'
6319 copy = {}
6345 copy = {}
6320 states = 'modified added removed deleted unknown ignored clean'.split()
6346 states = 'modified added removed deleted unknown ignored clean'.split()
6321 show = [k for k in states if opts.get(k)]
6347 show = [k for k in states if opts.get(k)]
6322 if opts.get('all'):
6348 if opts.get('all'):
6323 show += ui.quiet and (states[:4] + ['clean']) or states
6349 show += ui.quiet and (states[:4] + ['clean']) or states
6324 if not show:
6350 if not show:
6325 if ui.quiet:
6351 if ui.quiet:
6326 show = states[:4]
6352 show = states[:4]
6327 else:
6353 else:
6328 show = states[:5]
6354 show = states[:5]
6329
6355
6330 m = scmutil.match(repo[node2], pats, opts)
6356 m = scmutil.match(repo[node2], pats, opts)
6331 stat = repo.status(node1, node2, m,
6357 stat = repo.status(node1, node2, m,
6332 'ignored' in show, 'clean' in show, 'unknown' in show,
6358 'ignored' in show, 'clean' in show, 'unknown' in show,
6333 opts.get('subrepos'))
6359 opts.get('subrepos'))
6334 changestates = zip(states, 'MAR!?IC', stat)
6360 changestates = zip(states, 'MAR!?IC', stat)
6335
6361
6336 if (opts.get('all') or opts.get('copies')
6362 if (opts.get('all') or opts.get('copies')
6337 or ui.configbool('ui', 'statuscopies')) and not opts.get('no_status'):
6363 or ui.configbool('ui', 'statuscopies')) and not opts.get('no_status'):
6338 copy = copies.pathcopies(repo[node1], repo[node2], m)
6364 copy = copies.pathcopies(repo[node1], repo[node2], m)
6339
6365
6340 fm = ui.formatter('status', opts)
6366 fm = ui.formatter('status', opts)
6341 fmt = '%s' + end
6367 fmt = '%s' + end
6342 showchar = not opts.get('no_status')
6368 showchar = not opts.get('no_status')
6343
6369
6344 for state, char, files in changestates:
6370 for state, char, files in changestates:
6345 if state in show:
6371 if state in show:
6346 label = 'status.' + state
6372 label = 'status.' + state
6347 for f in files:
6373 for f in files:
6348 fm.startitem()
6374 fm.startitem()
6349 fm.condwrite(showchar, 'status', '%s ', char, label=label)
6375 fm.condwrite(showchar, 'status', '%s ', char, label=label)
6350 fm.write('path', fmt, repo.pathto(f, cwd), label=label)
6376 fm.write('path', fmt, repo.pathto(f, cwd), label=label)
6351 if f in copy:
6377 if f in copy:
6352 fm.write("copy", ' %s' + end, repo.pathto(copy[f], cwd),
6378 fm.write("copy", ' %s' + end, repo.pathto(copy[f], cwd),
6353 label='status.copied')
6379 label='status.copied')
6354 fm.end()
6380 fm.end()
6355
6381
6356 @command('^summary|sum',
6382 @command('^summary|sum',
6357 [('', 'remote', None, _('check for push and pull'))], '[--remote]')
6383 [('', 'remote', None, _('check for push and pull'))], '[--remote]')
6358 def summary(ui, repo, **opts):
6384 def summary(ui, repo, **opts):
6359 """summarize working directory state
6385 """summarize working directory state
6360
6386
6361 This generates a brief summary of the working directory state,
6387 This generates a brief summary of the working directory state,
6362 including parents, branch, commit status, phase and available updates.
6388 including parents, branch, commit status, phase and available updates.
6363
6389
6364 With the --remote option, this will check the default paths for
6390 With the --remote option, this will check the default paths for
6365 incoming and outgoing changes. This can be time-consuming.
6391 incoming and outgoing changes. This can be time-consuming.
6366
6392
6367 Returns 0 on success.
6393 Returns 0 on success.
6368 """
6394 """
6369
6395
6370 ctx = repo[None]
6396 ctx = repo[None]
6371 parents = ctx.parents()
6397 parents = ctx.parents()
6372 pnode = parents[0].node()
6398 pnode = parents[0].node()
6373 marks = []
6399 marks = []
6374
6400
6375 for p in parents:
6401 for p in parents:
6376 # label with log.changeset (instead of log.parent) since this
6402 # label with log.changeset (instead of log.parent) since this
6377 # shows a working directory parent *changeset*:
6403 # shows a working directory parent *changeset*:
6378 # i18n: column positioning for "hg summary"
6404 # i18n: column positioning for "hg summary"
6379 ui.write(_('parent: %d:%s ') % (p.rev(), str(p)),
6405 ui.write(_('parent: %d:%s ') % (p.rev(), str(p)),
6380 label='log.changeset changeset.%s' % p.phasestr())
6406 label='log.changeset changeset.%s' % p.phasestr())
6381 ui.write(' '.join(p.tags()), label='log.tag')
6407 ui.write(' '.join(p.tags()), label='log.tag')
6382 if p.bookmarks():
6408 if p.bookmarks():
6383 marks.extend(p.bookmarks())
6409 marks.extend(p.bookmarks())
6384 if p.rev() == -1:
6410 if p.rev() == -1:
6385 if not len(repo):
6411 if not len(repo):
6386 ui.write(_(' (empty repository)'))
6412 ui.write(_(' (empty repository)'))
6387 else:
6413 else:
6388 ui.write(_(' (no revision checked out)'))
6414 ui.write(_(' (no revision checked out)'))
6389 ui.write('\n')
6415 ui.write('\n')
6390 if p.description():
6416 if p.description():
6391 ui.status(' ' + p.description().splitlines()[0].strip() + '\n',
6417 ui.status(' ' + p.description().splitlines()[0].strip() + '\n',
6392 label='log.summary')
6418 label='log.summary')
6393
6419
6394 branch = ctx.branch()
6420 branch = ctx.branch()
6395 bheads = repo.branchheads(branch)
6421 bheads = repo.branchheads(branch)
6396 # i18n: column positioning for "hg summary"
6422 # i18n: column positioning for "hg summary"
6397 m = _('branch: %s\n') % branch
6423 m = _('branch: %s\n') % branch
6398 if branch != 'default':
6424 if branch != 'default':
6399 ui.write(m, label='log.branch')
6425 ui.write(m, label='log.branch')
6400 else:
6426 else:
6401 ui.status(m, label='log.branch')
6427 ui.status(m, label='log.branch')
6402
6428
6403 if marks:
6429 if marks:
6404 active = repo._activebookmark
6430 active = repo._activebookmark
6405 # i18n: column positioning for "hg summary"
6431 # i18n: column positioning for "hg summary"
6406 ui.write(_('bookmarks:'), label='log.bookmark')
6432 ui.write(_('bookmarks:'), label='log.bookmark')
6407 if active is not None:
6433 if active is not None:
6408 if active in marks:
6434 if active in marks:
6409 ui.write(' *' + active, label=activebookmarklabel)
6435 ui.write(' *' + active, label=activebookmarklabel)
6410 marks.remove(active)
6436 marks.remove(active)
6411 else:
6437 else:
6412 ui.write(' [%s]' % active, label=activebookmarklabel)
6438 ui.write(' [%s]' % active, label=activebookmarklabel)
6413 for m in marks:
6439 for m in marks:
6414 ui.write(' ' + m, label='log.bookmark')
6440 ui.write(' ' + m, label='log.bookmark')
6415 ui.write('\n', label='log.bookmark')
6441 ui.write('\n', label='log.bookmark')
6416
6442
6417 status = repo.status(unknown=True)
6443 status = repo.status(unknown=True)
6418
6444
6419 c = repo.dirstate.copies()
6445 c = repo.dirstate.copies()
6420 copied, renamed = [], []
6446 copied, renamed = [], []
6421 for d, s in c.iteritems():
6447 for d, s in c.iteritems():
6422 if s in status.removed:
6448 if s in status.removed:
6423 status.removed.remove(s)
6449 status.removed.remove(s)
6424 renamed.append(d)
6450 renamed.append(d)
6425 else:
6451 else:
6426 copied.append(d)
6452 copied.append(d)
6427 if d in status.added:
6453 if d in status.added:
6428 status.added.remove(d)
6454 status.added.remove(d)
6429
6455
6430 try:
6456 try:
6431 ms = mergemod.mergestate.read(repo)
6457 ms = mergemod.mergestate.read(repo)
6432 except error.UnsupportedMergeRecords as e:
6458 except error.UnsupportedMergeRecords as e:
6433 s = ' '.join(e.recordtypes)
6459 s = ' '.join(e.recordtypes)
6434 ui.warn(
6460 ui.warn(
6435 _('warning: merge state has unsupported record types: %s\n') % s)
6461 _('warning: merge state has unsupported record types: %s\n') % s)
6436 unresolved = 0
6462 unresolved = 0
6437 else:
6463 else:
6438 unresolved = [f for f in ms if ms[f] == 'u']
6464 unresolved = [f for f in ms if ms[f] == 'u']
6439
6465
6440 subs = [s for s in ctx.substate if ctx.sub(s).dirty()]
6466 subs = [s for s in ctx.substate if ctx.sub(s).dirty()]
6441
6467
6442 labels = [(ui.label(_('%d modified'), 'status.modified'), status.modified),
6468 labels = [(ui.label(_('%d modified'), 'status.modified'), status.modified),
6443 (ui.label(_('%d added'), 'status.added'), status.added),
6469 (ui.label(_('%d added'), 'status.added'), status.added),
6444 (ui.label(_('%d removed'), 'status.removed'), status.removed),
6470 (ui.label(_('%d removed'), 'status.removed'), status.removed),
6445 (ui.label(_('%d renamed'), 'status.copied'), renamed),
6471 (ui.label(_('%d renamed'), 'status.copied'), renamed),
6446 (ui.label(_('%d copied'), 'status.copied'), copied),
6472 (ui.label(_('%d copied'), 'status.copied'), copied),
6447 (ui.label(_('%d deleted'), 'status.deleted'), status.deleted),
6473 (ui.label(_('%d deleted'), 'status.deleted'), status.deleted),
6448 (ui.label(_('%d unknown'), 'status.unknown'), status.unknown),
6474 (ui.label(_('%d unknown'), 'status.unknown'), status.unknown),
6449 (ui.label(_('%d unresolved'), 'resolve.unresolved'), unresolved),
6475 (ui.label(_('%d unresolved'), 'resolve.unresolved'), unresolved),
6450 (ui.label(_('%d subrepos'), 'status.modified'), subs)]
6476 (ui.label(_('%d subrepos'), 'status.modified'), subs)]
6451 t = []
6477 t = []
6452 for l, s in labels:
6478 for l, s in labels:
6453 if s:
6479 if s:
6454 t.append(l % len(s))
6480 t.append(l % len(s))
6455
6481
6456 t = ', '.join(t)
6482 t = ', '.join(t)
6457 cleanworkdir = False
6483 cleanworkdir = False
6458
6484
6459 if repo.vfs.exists('graftstate'):
6485 if repo.vfs.exists('graftstate'):
6460 t += _(' (graft in progress)')
6486 t += _(' (graft in progress)')
6461 if repo.vfs.exists('updatestate'):
6487 if repo.vfs.exists('updatestate'):
6462 t += _(' (interrupted update)')
6488 t += _(' (interrupted update)')
6463 elif len(parents) > 1:
6489 elif len(parents) > 1:
6464 t += _(' (merge)')
6490 t += _(' (merge)')
6465 elif branch != parents[0].branch():
6491 elif branch != parents[0].branch():
6466 t += _(' (new branch)')
6492 t += _(' (new branch)')
6467 elif (parents[0].closesbranch() and
6493 elif (parents[0].closesbranch() and
6468 pnode in repo.branchheads(branch, closed=True)):
6494 pnode in repo.branchheads(branch, closed=True)):
6469 t += _(' (head closed)')
6495 t += _(' (head closed)')
6470 elif not (status.modified or status.added or status.removed or renamed or
6496 elif not (status.modified or status.added or status.removed or renamed or
6471 copied or subs):
6497 copied or subs):
6472 t += _(' (clean)')
6498 t += _(' (clean)')
6473 cleanworkdir = True
6499 cleanworkdir = True
6474 elif pnode not in bheads:
6500 elif pnode not in bheads:
6475 t += _(' (new branch head)')
6501 t += _(' (new branch head)')
6476
6502
6477 if parents:
6503 if parents:
6478 pendingphase = max(p.phase() for p in parents)
6504 pendingphase = max(p.phase() for p in parents)
6479 else:
6505 else:
6480 pendingphase = phases.public
6506 pendingphase = phases.public
6481
6507
6482 if pendingphase > phases.newcommitphase(ui):
6508 if pendingphase > phases.newcommitphase(ui):
6483 t += ' (%s)' % phases.phasenames[pendingphase]
6509 t += ' (%s)' % phases.phasenames[pendingphase]
6484
6510
6485 if cleanworkdir:
6511 if cleanworkdir:
6486 # i18n: column positioning for "hg summary"
6512 # i18n: column positioning for "hg summary"
6487 ui.status(_('commit: %s\n') % t.strip())
6513 ui.status(_('commit: %s\n') % t.strip())
6488 else:
6514 else:
6489 # i18n: column positioning for "hg summary"
6515 # i18n: column positioning for "hg summary"
6490 ui.write(_('commit: %s\n') % t.strip())
6516 ui.write(_('commit: %s\n') % t.strip())
6491
6517
6492 # all ancestors of branch heads - all ancestors of parent = new csets
6518 # all ancestors of branch heads - all ancestors of parent = new csets
6493 new = len(repo.changelog.findmissing([pctx.node() for pctx in parents],
6519 new = len(repo.changelog.findmissing([pctx.node() for pctx in parents],
6494 bheads))
6520 bheads))
6495
6521
6496 if new == 0:
6522 if new == 0:
6497 # i18n: column positioning for "hg summary"
6523 # i18n: column positioning for "hg summary"
6498 ui.status(_('update: (current)\n'))
6524 ui.status(_('update: (current)\n'))
6499 elif pnode not in bheads:
6525 elif pnode not in bheads:
6500 # i18n: column positioning for "hg summary"
6526 # i18n: column positioning for "hg summary"
6501 ui.write(_('update: %d new changesets (update)\n') % new)
6527 ui.write(_('update: %d new changesets (update)\n') % new)
6502 else:
6528 else:
6503 # i18n: column positioning for "hg summary"
6529 # i18n: column positioning for "hg summary"
6504 ui.write(_('update: %d new changesets, %d branch heads (merge)\n') %
6530 ui.write(_('update: %d new changesets, %d branch heads (merge)\n') %
6505 (new, len(bheads)))
6531 (new, len(bheads)))
6506
6532
6507 t = []
6533 t = []
6508 draft = len(repo.revs('draft()'))
6534 draft = len(repo.revs('draft()'))
6509 if draft:
6535 if draft:
6510 t.append(_('%d draft') % draft)
6536 t.append(_('%d draft') % draft)
6511 secret = len(repo.revs('secret()'))
6537 secret = len(repo.revs('secret()'))
6512 if secret:
6538 if secret:
6513 t.append(_('%d secret') % secret)
6539 t.append(_('%d secret') % secret)
6514
6540
6515 if draft or secret:
6541 if draft or secret:
6516 ui.status(_('phases: %s\n') % ', '.join(t))
6542 ui.status(_('phases: %s\n') % ', '.join(t))
6517
6543
6518 if obsolete.isenabled(repo, obsolete.createmarkersopt):
6544 if obsolete.isenabled(repo, obsolete.createmarkersopt):
6519 for trouble in ("unstable", "divergent", "bumped"):
6545 for trouble in ("unstable", "divergent", "bumped"):
6520 numtrouble = len(repo.revs(trouble + "()"))
6546 numtrouble = len(repo.revs(trouble + "()"))
6521 # We write all the possibilities to ease translation
6547 # We write all the possibilities to ease translation
6522 troublemsg = {
6548 troublemsg = {
6523 "unstable": _("unstable: %d changeset"),
6549 "unstable": _("unstable: %d changeset"),
6524 "divergent": _("divergent: %d changeset"),
6550 "divergent": _("divergent: %d changeset"),
6525 "bumped": _("bumped: %d changeset"),
6551 "bumped": _("bumped: %d changeset"),
6526 }
6552 }
6527 if numtrouble > 0:
6553 if numtrouble > 0:
6528 ui.status(troublemsg[trouble] % numtrouble + "\n")
6554 ui.status(troublemsg[trouble] % numtrouble + "\n")
6529
6555
6530 cmdutil.summaryhooks(ui, repo)
6556 cmdutil.summaryhooks(ui, repo)
6531
6557
6532 if opts.get('remote'):
6558 if opts.get('remote'):
6533 needsincoming, needsoutgoing = True, True
6559 needsincoming, needsoutgoing = True, True
6534 else:
6560 else:
6535 needsincoming, needsoutgoing = False, False
6561 needsincoming, needsoutgoing = False, False
6536 for i, o in cmdutil.summaryremotehooks(ui, repo, opts, None):
6562 for i, o in cmdutil.summaryremotehooks(ui, repo, opts, None):
6537 if i:
6563 if i:
6538 needsincoming = True
6564 needsincoming = True
6539 if o:
6565 if o:
6540 needsoutgoing = True
6566 needsoutgoing = True
6541 if not needsincoming and not needsoutgoing:
6567 if not needsincoming and not needsoutgoing:
6542 return
6568 return
6543
6569
6544 def getincoming():
6570 def getincoming():
6545 source, branches = hg.parseurl(ui.expandpath('default'))
6571 source, branches = hg.parseurl(ui.expandpath('default'))
6546 sbranch = branches[0]
6572 sbranch = branches[0]
6547 try:
6573 try:
6548 other = hg.peer(repo, {}, source)
6574 other = hg.peer(repo, {}, source)
6549 except error.RepoError:
6575 except error.RepoError:
6550 if opts.get('remote'):
6576 if opts.get('remote'):
6551 raise
6577 raise
6552 return source, sbranch, None, None, None
6578 return source, sbranch, None, None, None
6553 revs, checkout = hg.addbranchrevs(repo, other, branches, None)
6579 revs, checkout = hg.addbranchrevs(repo, other, branches, None)
6554 if revs:
6580 if revs:
6555 revs = [other.lookup(rev) for rev in revs]
6581 revs = [other.lookup(rev) for rev in revs]
6556 ui.debug('comparing with %s\n' % util.hidepassword(source))
6582 ui.debug('comparing with %s\n' % util.hidepassword(source))
6557 repo.ui.pushbuffer()
6583 repo.ui.pushbuffer()
6558 commoninc = discovery.findcommonincoming(repo, other, heads=revs)
6584 commoninc = discovery.findcommonincoming(repo, other, heads=revs)
6559 repo.ui.popbuffer()
6585 repo.ui.popbuffer()
6560 return source, sbranch, other, commoninc, commoninc[1]
6586 return source, sbranch, other, commoninc, commoninc[1]
6561
6587
6562 if needsincoming:
6588 if needsincoming:
6563 source, sbranch, sother, commoninc, incoming = getincoming()
6589 source, sbranch, sother, commoninc, incoming = getincoming()
6564 else:
6590 else:
6565 source = sbranch = sother = commoninc = incoming = None
6591 source = sbranch = sother = commoninc = incoming = None
6566
6592
6567 def getoutgoing():
6593 def getoutgoing():
6568 dest, branches = hg.parseurl(ui.expandpath('default-push', 'default'))
6594 dest, branches = hg.parseurl(ui.expandpath('default-push', 'default'))
6569 dbranch = branches[0]
6595 dbranch = branches[0]
6570 revs, checkout = hg.addbranchrevs(repo, repo, branches, None)
6596 revs, checkout = hg.addbranchrevs(repo, repo, branches, None)
6571 if source != dest:
6597 if source != dest:
6572 try:
6598 try:
6573 dother = hg.peer(repo, {}, dest)
6599 dother = hg.peer(repo, {}, dest)
6574 except error.RepoError:
6600 except error.RepoError:
6575 if opts.get('remote'):
6601 if opts.get('remote'):
6576 raise
6602 raise
6577 return dest, dbranch, None, None
6603 return dest, dbranch, None, None
6578 ui.debug('comparing with %s\n' % util.hidepassword(dest))
6604 ui.debug('comparing with %s\n' % util.hidepassword(dest))
6579 elif sother is None:
6605 elif sother is None:
6580 # there is no explicit destination peer, but source one is invalid
6606 # there is no explicit destination peer, but source one is invalid
6581 return dest, dbranch, None, None
6607 return dest, dbranch, None, None
6582 else:
6608 else:
6583 dother = sother
6609 dother = sother
6584 if (source != dest or (sbranch is not None and sbranch != dbranch)):
6610 if (source != dest or (sbranch is not None and sbranch != dbranch)):
6585 common = None
6611 common = None
6586 else:
6612 else:
6587 common = commoninc
6613 common = commoninc
6588 if revs:
6614 if revs:
6589 revs = [repo.lookup(rev) for rev in revs]
6615 revs = [repo.lookup(rev) for rev in revs]
6590 repo.ui.pushbuffer()
6616 repo.ui.pushbuffer()
6591 outgoing = discovery.findcommonoutgoing(repo, dother, onlyheads=revs,
6617 outgoing = discovery.findcommonoutgoing(repo, dother, onlyheads=revs,
6592 commoninc=common)
6618 commoninc=common)
6593 repo.ui.popbuffer()
6619 repo.ui.popbuffer()
6594 return dest, dbranch, dother, outgoing
6620 return dest, dbranch, dother, outgoing
6595
6621
6596 if needsoutgoing:
6622 if needsoutgoing:
6597 dest, dbranch, dother, outgoing = getoutgoing()
6623 dest, dbranch, dother, outgoing = getoutgoing()
6598 else:
6624 else:
6599 dest = dbranch = dother = outgoing = None
6625 dest = dbranch = dother = outgoing = None
6600
6626
6601 if opts.get('remote'):
6627 if opts.get('remote'):
6602 t = []
6628 t = []
6603 if incoming:
6629 if incoming:
6604 t.append(_('1 or more incoming'))
6630 t.append(_('1 or more incoming'))
6605 o = outgoing.missing
6631 o = outgoing.missing
6606 if o:
6632 if o:
6607 t.append(_('%d outgoing') % len(o))
6633 t.append(_('%d outgoing') % len(o))
6608 other = dother or sother
6634 other = dother or sother
6609 if 'bookmarks' in other.listkeys('namespaces'):
6635 if 'bookmarks' in other.listkeys('namespaces'):
6610 counts = bookmarks.summary(repo, other)
6636 counts = bookmarks.summary(repo, other)
6611 if counts[0] > 0:
6637 if counts[0] > 0:
6612 t.append(_('%d incoming bookmarks') % counts[0])
6638 t.append(_('%d incoming bookmarks') % counts[0])
6613 if counts[1] > 0:
6639 if counts[1] > 0:
6614 t.append(_('%d outgoing bookmarks') % counts[1])
6640 t.append(_('%d outgoing bookmarks') % counts[1])
6615
6641
6616 if t:
6642 if t:
6617 # i18n: column positioning for "hg summary"
6643 # i18n: column positioning for "hg summary"
6618 ui.write(_('remote: %s\n') % (', '.join(t)))
6644 ui.write(_('remote: %s\n') % (', '.join(t)))
6619 else:
6645 else:
6620 # i18n: column positioning for "hg summary"
6646 # i18n: column positioning for "hg summary"
6621 ui.status(_('remote: (synced)\n'))
6647 ui.status(_('remote: (synced)\n'))
6622
6648
6623 cmdutil.summaryremotehooks(ui, repo, opts,
6649 cmdutil.summaryremotehooks(ui, repo, opts,
6624 ((source, sbranch, sother, commoninc),
6650 ((source, sbranch, sother, commoninc),
6625 (dest, dbranch, dother, outgoing)))
6651 (dest, dbranch, dother, outgoing)))
6626
6652
6627 @command('tag',
6653 @command('tag',
6628 [('f', 'force', None, _('force tag')),
6654 [('f', 'force', None, _('force tag')),
6629 ('l', 'local', None, _('make the tag local')),
6655 ('l', 'local', None, _('make the tag local')),
6630 ('r', 'rev', '', _('revision to tag'), _('REV')),
6656 ('r', 'rev', '', _('revision to tag'), _('REV')),
6631 ('', 'remove', None, _('remove a tag')),
6657 ('', 'remove', None, _('remove a tag')),
6632 # -l/--local is already there, commitopts cannot be used
6658 # -l/--local is already there, commitopts cannot be used
6633 ('e', 'edit', None, _('invoke editor on commit messages')),
6659 ('e', 'edit', None, _('invoke editor on commit messages')),
6634 ('m', 'message', '', _('use text as commit message'), _('TEXT')),
6660 ('m', 'message', '', _('use text as commit message'), _('TEXT')),
6635 ] + commitopts2,
6661 ] + commitopts2,
6636 _('[-f] [-l] [-m TEXT] [-d DATE] [-u USER] [-r REV] NAME...'))
6662 _('[-f] [-l] [-m TEXT] [-d DATE] [-u USER] [-r REV] NAME...'))
6637 def tag(ui, repo, name1, *names, **opts):
6663 def tag(ui, repo, name1, *names, **opts):
6638 """add one or more tags for the current or given revision
6664 """add one or more tags for the current or given revision
6639
6665
6640 Name a particular revision using <name>.
6666 Name a particular revision using <name>.
6641
6667
6642 Tags are used to name particular revisions of the repository and are
6668 Tags are used to name particular revisions of the repository and are
6643 very useful to compare different revisions, to go back to significant
6669 very useful to compare different revisions, to go back to significant
6644 earlier versions or to mark branch points as releases, etc. Changing
6670 earlier versions or to mark branch points as releases, etc. Changing
6645 an existing tag is normally disallowed; use -f/--force to override.
6671 an existing tag is normally disallowed; use -f/--force to override.
6646
6672
6647 If no revision is given, the parent of the working directory is
6673 If no revision is given, the parent of the working directory is
6648 used.
6674 used.
6649
6675
6650 To facilitate version control, distribution, and merging of tags,
6676 To facilitate version control, distribution, and merging of tags,
6651 they are stored as a file named ".hgtags" which is managed similarly
6677 they are stored as a file named ".hgtags" which is managed similarly
6652 to other project files and can be hand-edited if necessary. This
6678 to other project files and can be hand-edited if necessary. This
6653 also means that tagging creates a new commit. The file
6679 also means that tagging creates a new commit. The file
6654 ".hg/localtags" is used for local tags (not shared among
6680 ".hg/localtags" is used for local tags (not shared among
6655 repositories).
6681 repositories).
6656
6682
6657 Tag commits are usually made at the head of a branch. If the parent
6683 Tag commits are usually made at the head of a branch. If the parent
6658 of the working directory is not a branch head, :hg:`tag` aborts; use
6684 of the working directory is not a branch head, :hg:`tag` aborts; use
6659 -f/--force to force the tag commit to be based on a non-head
6685 -f/--force to force the tag commit to be based on a non-head
6660 changeset.
6686 changeset.
6661
6687
6662 See :hg:`help dates` for a list of formats valid for -d/--date.
6688 See :hg:`help dates` for a list of formats valid for -d/--date.
6663
6689
6664 Since tag names have priority over branch names during revision
6690 Since tag names have priority over branch names during revision
6665 lookup, using an existing branch name as a tag name is discouraged.
6691 lookup, using an existing branch name as a tag name is discouraged.
6666
6692
6667 Returns 0 on success.
6693 Returns 0 on success.
6668 """
6694 """
6669 wlock = lock = None
6695 wlock = lock = None
6670 try:
6696 try:
6671 wlock = repo.wlock()
6697 wlock = repo.wlock()
6672 lock = repo.lock()
6698 lock = repo.lock()
6673 rev_ = "."
6699 rev_ = "."
6674 names = [t.strip() for t in (name1,) + names]
6700 names = [t.strip() for t in (name1,) + names]
6675 if len(names) != len(set(names)):
6701 if len(names) != len(set(names)):
6676 raise error.Abort(_('tag names must be unique'))
6702 raise error.Abort(_('tag names must be unique'))
6677 for n in names:
6703 for n in names:
6678 scmutil.checknewlabel(repo, n, 'tag')
6704 scmutil.checknewlabel(repo, n, 'tag')
6679 if not n:
6705 if not n:
6680 raise error.Abort(_('tag names cannot consist entirely of '
6706 raise error.Abort(_('tag names cannot consist entirely of '
6681 'whitespace'))
6707 'whitespace'))
6682 if opts.get('rev') and opts.get('remove'):
6708 if opts.get('rev') and opts.get('remove'):
6683 raise error.Abort(_("--rev and --remove are incompatible"))
6709 raise error.Abort(_("--rev and --remove are incompatible"))
6684 if opts.get('rev'):
6710 if opts.get('rev'):
6685 rev_ = opts['rev']
6711 rev_ = opts['rev']
6686 message = opts.get('message')
6712 message = opts.get('message')
6687 if opts.get('remove'):
6713 if opts.get('remove'):
6688 if opts.get('local'):
6714 if opts.get('local'):
6689 expectedtype = 'local'
6715 expectedtype = 'local'
6690 else:
6716 else:
6691 expectedtype = 'global'
6717 expectedtype = 'global'
6692
6718
6693 for n in names:
6719 for n in names:
6694 if not repo.tagtype(n):
6720 if not repo.tagtype(n):
6695 raise error.Abort(_("tag '%s' does not exist") % n)
6721 raise error.Abort(_("tag '%s' does not exist") % n)
6696 if repo.tagtype(n) != expectedtype:
6722 if repo.tagtype(n) != expectedtype:
6697 if expectedtype == 'global':
6723 if expectedtype == 'global':
6698 raise error.Abort(_("tag '%s' is not a global tag") % n)
6724 raise error.Abort(_("tag '%s' is not a global tag") % n)
6699 else:
6725 else:
6700 raise error.Abort(_("tag '%s' is not a local tag") % n)
6726 raise error.Abort(_("tag '%s' is not a local tag") % n)
6701 rev_ = 'null'
6727 rev_ = 'null'
6702 if not message:
6728 if not message:
6703 # we don't translate commit messages
6729 # we don't translate commit messages
6704 message = 'Removed tag %s' % ', '.join(names)
6730 message = 'Removed tag %s' % ', '.join(names)
6705 elif not opts.get('force'):
6731 elif not opts.get('force'):
6706 for n in names:
6732 for n in names:
6707 if n in repo.tags():
6733 if n in repo.tags():
6708 raise error.Abort(_("tag '%s' already exists "
6734 raise error.Abort(_("tag '%s' already exists "
6709 "(use -f to force)") % n)
6735 "(use -f to force)") % n)
6710 if not opts.get('local'):
6736 if not opts.get('local'):
6711 p1, p2 = repo.dirstate.parents()
6737 p1, p2 = repo.dirstate.parents()
6712 if p2 != nullid:
6738 if p2 != nullid:
6713 raise error.Abort(_('uncommitted merge'))
6739 raise error.Abort(_('uncommitted merge'))
6714 bheads = repo.branchheads()
6740 bheads = repo.branchheads()
6715 if not opts.get('force') and bheads and p1 not in bheads:
6741 if not opts.get('force') and bheads and p1 not in bheads:
6716 raise error.Abort(_('not at a branch head (use -f to force)'))
6742 raise error.Abort(_('not at a branch head (use -f to force)'))
6717 r = scmutil.revsingle(repo, rev_).node()
6743 r = scmutil.revsingle(repo, rev_).node()
6718
6744
6719 if not message:
6745 if not message:
6720 # we don't translate commit messages
6746 # we don't translate commit messages
6721 message = ('Added tag %s for changeset %s' %
6747 message = ('Added tag %s for changeset %s' %
6722 (', '.join(names), short(r)))
6748 (', '.join(names), short(r)))
6723
6749
6724 date = opts.get('date')
6750 date = opts.get('date')
6725 if date:
6751 if date:
6726 date = util.parsedate(date)
6752 date = util.parsedate(date)
6727
6753
6728 if opts.get('remove'):
6754 if opts.get('remove'):
6729 editform = 'tag.remove'
6755 editform = 'tag.remove'
6730 else:
6756 else:
6731 editform = 'tag.add'
6757 editform = 'tag.add'
6732 editor = cmdutil.getcommiteditor(editform=editform, **opts)
6758 editor = cmdutil.getcommiteditor(editform=editform, **opts)
6733
6759
6734 # don't allow tagging the null rev
6760 # don't allow tagging the null rev
6735 if (not opts.get('remove') and
6761 if (not opts.get('remove') and
6736 scmutil.revsingle(repo, rev_).rev() == nullrev):
6762 scmutil.revsingle(repo, rev_).rev() == nullrev):
6737 raise error.Abort(_("cannot tag null revision"))
6763 raise error.Abort(_("cannot tag null revision"))
6738
6764
6739 repo.tag(names, r, message, opts.get('local'), opts.get('user'), date,
6765 repo.tag(names, r, message, opts.get('local'), opts.get('user'), date,
6740 editor=editor)
6766 editor=editor)
6741 finally:
6767 finally:
6742 release(lock, wlock)
6768 release(lock, wlock)
6743
6769
6744 @command('tags', formatteropts, '')
6770 @command('tags', formatteropts, '')
6745 def tags(ui, repo, **opts):
6771 def tags(ui, repo, **opts):
6746 """list repository tags
6772 """list repository tags
6747
6773
6748 This lists both regular and local tags. When the -v/--verbose
6774 This lists both regular and local tags. When the -v/--verbose
6749 switch is used, a third column "local" is printed for local tags.
6775 switch is used, a third column "local" is printed for local tags.
6750 When the -q/--quiet switch is used, only the tag name is printed.
6776 When the -q/--quiet switch is used, only the tag name is printed.
6751
6777
6752 Returns 0 on success.
6778 Returns 0 on success.
6753 """
6779 """
6754
6780
6755 fm = ui.formatter('tags', opts)
6781 fm = ui.formatter('tags', opts)
6756 hexfunc = fm.hexfunc
6782 hexfunc = fm.hexfunc
6757 tagtype = ""
6783 tagtype = ""
6758
6784
6759 for t, n in reversed(repo.tagslist()):
6785 for t, n in reversed(repo.tagslist()):
6760 hn = hexfunc(n)
6786 hn = hexfunc(n)
6761 label = 'tags.normal'
6787 label = 'tags.normal'
6762 tagtype = ''
6788 tagtype = ''
6763 if repo.tagtype(t) == 'local':
6789 if repo.tagtype(t) == 'local':
6764 label = 'tags.local'
6790 label = 'tags.local'
6765 tagtype = 'local'
6791 tagtype = 'local'
6766
6792
6767 fm.startitem()
6793 fm.startitem()
6768 fm.write('tag', '%s', t, label=label)
6794 fm.write('tag', '%s', t, label=label)
6769 fmt = " " * (30 - encoding.colwidth(t)) + ' %5d:%s'
6795 fmt = " " * (30 - encoding.colwidth(t)) + ' %5d:%s'
6770 fm.condwrite(not ui.quiet, 'rev node', fmt,
6796 fm.condwrite(not ui.quiet, 'rev node', fmt,
6771 repo.changelog.rev(n), hn, label=label)
6797 repo.changelog.rev(n), hn, label=label)
6772 fm.condwrite(ui.verbose and tagtype, 'type', ' %s',
6798 fm.condwrite(ui.verbose and tagtype, 'type', ' %s',
6773 tagtype, label=label)
6799 tagtype, label=label)
6774 fm.plain('\n')
6800 fm.plain('\n')
6775 fm.end()
6801 fm.end()
6776
6802
6777 @command('tip',
6803 @command('tip',
6778 [('p', 'patch', None, _('show patch')),
6804 [('p', 'patch', None, _('show patch')),
6779 ('g', 'git', None, _('use git extended diff format')),
6805 ('g', 'git', None, _('use git extended diff format')),
6780 ] + templateopts,
6806 ] + templateopts,
6781 _('[-p] [-g]'))
6807 _('[-p] [-g]'))
6782 def tip(ui, repo, **opts):
6808 def tip(ui, repo, **opts):
6783 """show the tip revision (DEPRECATED)
6809 """show the tip revision (DEPRECATED)
6784
6810
6785 The tip revision (usually just called the tip) is the changeset
6811 The tip revision (usually just called the tip) is the changeset
6786 most recently added to the repository (and therefore the most
6812 most recently added to the repository (and therefore the most
6787 recently changed head).
6813 recently changed head).
6788
6814
6789 If you have just made a commit, that commit will be the tip. If
6815 If you have just made a commit, that commit will be the tip. If
6790 you have just pulled changes from another repository, the tip of
6816 you have just pulled changes from another repository, the tip of
6791 that repository becomes the current tip. The "tip" tag is special
6817 that repository becomes the current tip. The "tip" tag is special
6792 and cannot be renamed or assigned to a different changeset.
6818 and cannot be renamed or assigned to a different changeset.
6793
6819
6794 This command is deprecated, please use :hg:`heads` instead.
6820 This command is deprecated, please use :hg:`heads` instead.
6795
6821
6796 Returns 0 on success.
6822 Returns 0 on success.
6797 """
6823 """
6798 displayer = cmdutil.show_changeset(ui, repo, opts)
6824 displayer = cmdutil.show_changeset(ui, repo, opts)
6799 displayer.show(repo['tip'])
6825 displayer.show(repo['tip'])
6800 displayer.close()
6826 displayer.close()
6801
6827
6802 @command('unbundle',
6828 @command('unbundle',
6803 [('u', 'update', None,
6829 [('u', 'update', None,
6804 _('update to new branch head if changesets were unbundled'))],
6830 _('update to new branch head if changesets were unbundled'))],
6805 _('[-u] FILE...'))
6831 _('[-u] FILE...'))
6806 def unbundle(ui, repo, fname1, *fnames, **opts):
6832 def unbundle(ui, repo, fname1, *fnames, **opts):
6807 """apply one or more changegroup files
6833 """apply one or more changegroup files
6808
6834
6809 Apply one or more compressed changegroup files generated by the
6835 Apply one or more compressed changegroup files generated by the
6810 bundle command.
6836 bundle command.
6811
6837
6812 Returns 0 on success, 1 if an update has unresolved files.
6838 Returns 0 on success, 1 if an update has unresolved files.
6813 """
6839 """
6814 fnames = (fname1,) + fnames
6840 fnames = (fname1,) + fnames
6815
6841
6816 lock = repo.lock()
6842 lock = repo.lock()
6817 try:
6843 try:
6818 for fname in fnames:
6844 for fname in fnames:
6819 f = hg.openpath(ui, fname)
6845 f = hg.openpath(ui, fname)
6820 gen = exchange.readbundle(ui, f, fname)
6846 gen = exchange.readbundle(ui, f, fname)
6821 if isinstance(gen, bundle2.unbundle20):
6847 if isinstance(gen, bundle2.unbundle20):
6822 tr = repo.transaction('unbundle')
6848 tr = repo.transaction('unbundle')
6823 try:
6849 try:
6824 op = bundle2.applybundle(repo, gen, tr, source='unbundle',
6850 op = bundle2.applybundle(repo, gen, tr, source='unbundle',
6825 url='bundle:' + fname)
6851 url='bundle:' + fname)
6826 tr.close()
6852 tr.close()
6827 except error.BundleUnknownFeatureError as exc:
6853 except error.BundleUnknownFeatureError as exc:
6828 raise error.Abort(_('%s: unknown bundle feature, %s')
6854 raise error.Abort(_('%s: unknown bundle feature, %s')
6829 % (fname, exc),
6855 % (fname, exc),
6830 hint=_("see https://mercurial-scm.org/"
6856 hint=_("see https://mercurial-scm.org/"
6831 "wiki/BundleFeature for more "
6857 "wiki/BundleFeature for more "
6832 "information"))
6858 "information"))
6833 finally:
6859 finally:
6834 if tr:
6860 if tr:
6835 tr.release()
6861 tr.release()
6836 changes = [r.get('return', 0)
6862 changes = [r.get('return', 0)
6837 for r in op.records['changegroup']]
6863 for r in op.records['changegroup']]
6838 modheads = changegroup.combineresults(changes)
6864 modheads = changegroup.combineresults(changes)
6839 elif isinstance(gen, streamclone.streamcloneapplier):
6865 elif isinstance(gen, streamclone.streamcloneapplier):
6840 raise error.Abort(
6866 raise error.Abort(
6841 _('packed bundles cannot be applied with '
6867 _('packed bundles cannot be applied with '
6842 '"hg unbundle"'),
6868 '"hg unbundle"'),
6843 hint=_('use "hg debugapplystreamclonebundle"'))
6869 hint=_('use "hg debugapplystreamclonebundle"'))
6844 else:
6870 else:
6845 modheads = gen.apply(repo, 'unbundle', 'bundle:' + fname)
6871 modheads = gen.apply(repo, 'unbundle', 'bundle:' + fname)
6846 finally:
6872 finally:
6847 lock.release()
6873 lock.release()
6848
6874
6849 return postincoming(ui, repo, modheads, opts.get('update'), None)
6875 return postincoming(ui, repo, modheads, opts.get('update'), None)
6850
6876
6851 @command('^update|up|checkout|co',
6877 @command('^update|up|checkout|co',
6852 [('C', 'clean', None, _('discard uncommitted changes (no backup)')),
6878 [('C', 'clean', None, _('discard uncommitted changes (no backup)')),
6853 ('c', 'check', None,
6879 ('c', 'check', None,
6854 _('update across branches if no uncommitted changes')),
6880 _('update across branches if no uncommitted changes')),
6855 ('d', 'date', '', _('tipmost revision matching date'), _('DATE')),
6881 ('d', 'date', '', _('tipmost revision matching date'), _('DATE')),
6856 ('r', 'rev', '', _('revision'), _('REV'))
6882 ('r', 'rev', '', _('revision'), _('REV'))
6857 ] + mergetoolopts,
6883 ] + mergetoolopts,
6858 _('[-c] [-C] [-d DATE] [[-r] REV]'))
6884 _('[-c] [-C] [-d DATE] [[-r] REV]'))
6859 def update(ui, repo, node=None, rev=None, clean=False, date=None, check=False,
6885 def update(ui, repo, node=None, rev=None, clean=False, date=None, check=False,
6860 tool=None):
6886 tool=None):
6861 """update working directory (or switch revisions)
6887 """update working directory (or switch revisions)
6862
6888
6863 Update the repository's working directory to the specified
6889 Update the repository's working directory to the specified
6864 changeset. If no changeset is specified, update to the tip of the
6890 changeset. If no changeset is specified, update to the tip of the
6865 current named branch and move the active bookmark (see :hg:`help
6891 current named branch and move the active bookmark (see :hg:`help
6866 bookmarks`).
6892 bookmarks`).
6867
6893
6868 Update sets the working directory's parent revision to the specified
6894 Update sets the working directory's parent revision to the specified
6869 changeset (see :hg:`help parents`).
6895 changeset (see :hg:`help parents`).
6870
6896
6871 If the changeset is not a descendant or ancestor of the working
6897 If the changeset is not a descendant or ancestor of the working
6872 directory's parent, the update is aborted. With the -c/--check
6898 directory's parent, the update is aborted. With the -c/--check
6873 option, the working directory is checked for uncommitted changes; if
6899 option, the working directory is checked for uncommitted changes; if
6874 none are found, the working directory is updated to the specified
6900 none are found, the working directory is updated to the specified
6875 changeset.
6901 changeset.
6876
6902
6877 .. container:: verbose
6903 .. container:: verbose
6878
6904
6879 The following rules apply when the working directory contains
6905 The following rules apply when the working directory contains
6880 uncommitted changes:
6906 uncommitted changes:
6881
6907
6882 1. If neither -c/--check nor -C/--clean is specified, and if
6908 1. If neither -c/--check nor -C/--clean is specified, and if
6883 the requested changeset is an ancestor or descendant of
6909 the requested changeset is an ancestor or descendant of
6884 the working directory's parent, the uncommitted changes
6910 the working directory's parent, the uncommitted changes
6885 are merged into the requested changeset and the merged
6911 are merged into the requested changeset and the merged
6886 result is left uncommitted. If the requested changeset is
6912 result is left uncommitted. If the requested changeset is
6887 not an ancestor or descendant (that is, it is on another
6913 not an ancestor or descendant (that is, it is on another
6888 branch), the update is aborted and the uncommitted changes
6914 branch), the update is aborted and the uncommitted changes
6889 are preserved.
6915 are preserved.
6890
6916
6891 2. With the -c/--check option, the update is aborted and the
6917 2. With the -c/--check option, the update is aborted and the
6892 uncommitted changes are preserved.
6918 uncommitted changes are preserved.
6893
6919
6894 3. With the -C/--clean option, uncommitted changes are discarded and
6920 3. With the -C/--clean option, uncommitted changes are discarded and
6895 the working directory is updated to the requested changeset.
6921 the working directory is updated to the requested changeset.
6896
6922
6897 To cancel an uncommitted merge (and lose your changes), use
6923 To cancel an uncommitted merge (and lose your changes), use
6898 :hg:`update --clean .`.
6924 :hg:`update --clean .`.
6899
6925
6900 Use null as the changeset to remove the working directory (like
6926 Use null as the changeset to remove the working directory (like
6901 :hg:`clone -U`).
6927 :hg:`clone -U`).
6902
6928
6903 If you want to revert just one file to an older revision, use
6929 If you want to revert just one file to an older revision, use
6904 :hg:`revert [-r REV] NAME`.
6930 :hg:`revert [-r REV] NAME`.
6905
6931
6906 See :hg:`help dates` for a list of formats valid for -d/--date.
6932 See :hg:`help dates` for a list of formats valid for -d/--date.
6907
6933
6908 Returns 0 on success, 1 if there are unresolved files.
6934 Returns 0 on success, 1 if there are unresolved files.
6909 """
6935 """
6910 movemarkfrom = None
6936 movemarkfrom = None
6911 if rev and node:
6937 if rev and node:
6912 raise error.Abort(_("please specify just one revision"))
6938 raise error.Abort(_("please specify just one revision"))
6913
6939
6914 if rev is None or rev == '':
6940 if rev is None or rev == '':
6915 rev = node
6941 rev = node
6916
6942
6917 wlock = repo.wlock()
6943 wlock = repo.wlock()
6918 try:
6944 try:
6919 cmdutil.clearunfinished(repo)
6945 cmdutil.clearunfinished(repo)
6920
6946
6921 if date:
6947 if date:
6922 if rev is not None:
6948 if rev is not None:
6923 raise error.Abort(_("you can't specify a revision and a date"))
6949 raise error.Abort(_("you can't specify a revision and a date"))
6924 rev = cmdutil.finddate(ui, repo, date)
6950 rev = cmdutil.finddate(ui, repo, date)
6925
6951
6926 # if we defined a bookmark, we have to remember the original name
6952 # if we defined a bookmark, we have to remember the original name
6927 brev = rev
6953 brev = rev
6928 rev = scmutil.revsingle(repo, rev, rev).rev()
6954 rev = scmutil.revsingle(repo, rev, rev).rev()
6929
6955
6930 if check and clean:
6956 if check and clean:
6931 raise error.Abort(_("cannot specify both -c/--check and -C/--clean")
6957 raise error.Abort(_("cannot specify both -c/--check and -C/--clean")
6932 )
6958 )
6933
6959
6934 if check:
6960 if check:
6935 cmdutil.bailifchanged(repo, merge=False)
6961 cmdutil.bailifchanged(repo, merge=False)
6936 if rev is None:
6962 if rev is None:
6937 updata = destutil.destupdate(repo, clean=clean, check=check)
6963 updata = destutil.destupdate(repo, clean=clean, check=check)
6938 rev, movemarkfrom, brev = updata
6964 rev, movemarkfrom, brev = updata
6939
6965
6940 repo.ui.setconfig('ui', 'forcemerge', tool, 'update')
6966 repo.ui.setconfig('ui', 'forcemerge', tool, 'update')
6941
6967
6942 if clean:
6968 if clean:
6943 ret = hg.clean(repo, rev)
6969 ret = hg.clean(repo, rev)
6944 else:
6970 else:
6945 ret = hg.update(repo, rev)
6971 ret = hg.update(repo, rev)
6946
6972
6947 if not ret and movemarkfrom:
6973 if not ret and movemarkfrom:
6948 if movemarkfrom == repo['.'].node():
6974 if movemarkfrom == repo['.'].node():
6949 pass # no-op update
6975 pass # no-op update
6950 elif bookmarks.update(repo, [movemarkfrom], repo['.'].node()):
6976 elif bookmarks.update(repo, [movemarkfrom], repo['.'].node()):
6951 ui.status(_("updating bookmark %s\n") % repo._activebookmark)
6977 ui.status(_("updating bookmark %s\n") % repo._activebookmark)
6952 else:
6978 else:
6953 # this can happen with a non-linear update
6979 # this can happen with a non-linear update
6954 ui.status(_("(leaving bookmark %s)\n") %
6980 ui.status(_("(leaving bookmark %s)\n") %
6955 repo._activebookmark)
6981 repo._activebookmark)
6956 bookmarks.deactivate(repo)
6982 bookmarks.deactivate(repo)
6957 elif brev in repo._bookmarks:
6983 elif brev in repo._bookmarks:
6958 bookmarks.activate(repo, brev)
6984 bookmarks.activate(repo, brev)
6959 ui.status(_("(activating bookmark %s)\n") % brev)
6985 ui.status(_("(activating bookmark %s)\n") % brev)
6960 elif brev:
6986 elif brev:
6961 if repo._activebookmark:
6987 if repo._activebookmark:
6962 ui.status(_("(leaving bookmark %s)\n") %
6988 ui.status(_("(leaving bookmark %s)\n") %
6963 repo._activebookmark)
6989 repo._activebookmark)
6964 bookmarks.deactivate(repo)
6990 bookmarks.deactivate(repo)
6965 finally:
6991 finally:
6966 wlock.release()
6992 wlock.release()
6967
6993
6968 return ret
6994 return ret
6969
6995
6970 @command('verify', [])
6996 @command('verify', [])
6971 def verify(ui, repo):
6997 def verify(ui, repo):
6972 """verify the integrity of the repository
6998 """verify the integrity of the repository
6973
6999
6974 Verify the integrity of the current repository.
7000 Verify the integrity of the current repository.
6975
7001
6976 This will perform an extensive check of the repository's
7002 This will perform an extensive check of the repository's
6977 integrity, validating the hashes and checksums of each entry in
7003 integrity, validating the hashes and checksums of each entry in
6978 the changelog, manifest, and tracked files, as well as the
7004 the changelog, manifest, and tracked files, as well as the
6979 integrity of their crosslinks and indices.
7005 integrity of their crosslinks and indices.
6980
7006
6981 Please see https://mercurial-scm.org/wiki/RepositoryCorruption
7007 Please see https://mercurial-scm.org/wiki/RepositoryCorruption
6982 for more information about recovery from corruption of the
7008 for more information about recovery from corruption of the
6983 repository.
7009 repository.
6984
7010
6985 Returns 0 on success, 1 if errors are encountered.
7011 Returns 0 on success, 1 if errors are encountered.
6986 """
7012 """
6987 return hg.verify(repo)
7013 return hg.verify(repo)
6988
7014
6989 @command('version', [], norepo=True)
7015 @command('version', [], norepo=True)
6990 def version_(ui):
7016 def version_(ui):
6991 """output version and copyright information"""
7017 """output version and copyright information"""
6992 ui.write(_("Mercurial Distributed SCM (version %s)\n")
7018 ui.write(_("Mercurial Distributed SCM (version %s)\n")
6993 % util.version())
7019 % util.version())
6994 ui.status(_(
7020 ui.status(_(
6995 "(see https://mercurial-scm.org for more information)\n"
7021 "(see https://mercurial-scm.org for more information)\n"
6996 "\nCopyright (C) 2005-2015 Matt Mackall and others\n"
7022 "\nCopyright (C) 2005-2015 Matt Mackall and others\n"
6997 "This is free software; see the source for copying conditions. "
7023 "This is free software; see the source for copying conditions. "
6998 "There is NO\nwarranty; "
7024 "There is NO\nwarranty; "
6999 "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n"
7025 "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n"
7000 ))
7026 ))
7001
7027
7002 ui.note(_("\nEnabled extensions:\n\n"))
7028 ui.note(_("\nEnabled extensions:\n\n"))
7003 if ui.verbose:
7029 if ui.verbose:
7004 # format names and versions into columns
7030 # format names and versions into columns
7005 names = []
7031 names = []
7006 vers = []
7032 vers = []
7007 for name, module in extensions.extensions():
7033 for name, module in extensions.extensions():
7008 names.append(name)
7034 names.append(name)
7009 vers.append(extensions.moduleversion(module))
7035 vers.append(extensions.moduleversion(module))
7010 if names:
7036 if names:
7011 maxnamelen = max(len(n) for n in names)
7037 maxnamelen = max(len(n) for n in names)
7012 for i, name in enumerate(names):
7038 for i, name in enumerate(names):
7013 ui.write(" %-*s %s\n" % (maxnamelen, name, vers[i]))
7039 ui.write(" %-*s %s\n" % (maxnamelen, name, vers[i]))
@@ -1,2985 +1,2986 b''
1 Short help:
1 Short help:
2
2
3 $ hg
3 $ hg
4 Mercurial Distributed SCM
4 Mercurial Distributed SCM
5
5
6 basic commands:
6 basic commands:
7
7
8 add add the specified files on the next commit
8 add add the specified files on the next commit
9 annotate show changeset information by line for each file
9 annotate show changeset information by line for each file
10 clone make a copy of an existing repository
10 clone make a copy of an existing repository
11 commit commit the specified files or all outstanding changes
11 commit commit the specified files or all outstanding changes
12 diff diff repository (or selected files)
12 diff diff repository (or selected files)
13 export dump the header and diffs for one or more changesets
13 export dump the header and diffs for one or more changesets
14 forget forget the specified files on the next commit
14 forget forget the specified files on the next commit
15 init create a new repository in the given directory
15 init create a new repository in the given directory
16 log show revision history of entire repository or files
16 log show revision history of entire repository or files
17 merge merge another revision into working directory
17 merge merge another revision into working directory
18 pull pull changes from the specified source
18 pull pull changes from the specified source
19 push push changes to the specified destination
19 push push changes to the specified destination
20 remove remove the specified files on the next commit
20 remove remove the specified files on the next commit
21 serve start stand-alone webserver
21 serve start stand-alone webserver
22 status show changed files in the working directory
22 status show changed files in the working directory
23 summary summarize working directory state
23 summary summarize working directory state
24 update update working directory (or switch revisions)
24 update update working directory (or switch revisions)
25
25
26 (use "hg help" for the full list of commands or "hg -v" for details)
26 (use "hg help" for the full list of commands or "hg -v" for details)
27
27
28 $ hg -q
28 $ hg -q
29 add add the specified files on the next commit
29 add add the specified files on the next commit
30 annotate show changeset information by line for each file
30 annotate show changeset information by line for each file
31 clone make a copy of an existing repository
31 clone make a copy of an existing repository
32 commit commit the specified files or all outstanding changes
32 commit commit the specified files or all outstanding changes
33 diff diff repository (or selected files)
33 diff diff repository (or selected files)
34 export dump the header and diffs for one or more changesets
34 export dump the header and diffs for one or more changesets
35 forget forget the specified files on the next commit
35 forget forget the specified files on the next commit
36 init create a new repository in the given directory
36 init create a new repository in the given directory
37 log show revision history of entire repository or files
37 log show revision history of entire repository or files
38 merge merge another revision into working directory
38 merge merge another revision into working directory
39 pull pull changes from the specified source
39 pull pull changes from the specified source
40 push push changes to the specified destination
40 push push changes to the specified destination
41 remove remove the specified files on the next commit
41 remove remove the specified files on the next commit
42 serve start stand-alone webserver
42 serve start stand-alone webserver
43 status show changed files in the working directory
43 status show changed files in the working directory
44 summary summarize working directory state
44 summary summarize working directory state
45 update update working directory (or switch revisions)
45 update update working directory (or switch revisions)
46
46
47 $ hg help
47 $ hg help
48 Mercurial Distributed SCM
48 Mercurial Distributed SCM
49
49
50 list of commands:
50 list of commands:
51
51
52 add add the specified files on the next commit
52 add add the specified files on the next commit
53 addremove add all new files, delete all missing files
53 addremove add all new files, delete all missing files
54 annotate show changeset information by line for each file
54 annotate show changeset information by line for each file
55 archive create an unversioned archive of a repository revision
55 archive create an unversioned archive of a repository revision
56 backout reverse effect of earlier changeset
56 backout reverse effect of earlier changeset
57 bisect subdivision search of changesets
57 bisect subdivision search of changesets
58 bookmarks create a new bookmark or list existing bookmarks
58 bookmarks create a new bookmark or list existing bookmarks
59 branch set or show the current branch name
59 branch set or show the current branch name
60 branches list repository named branches
60 branches list repository named branches
61 bundle create a changegroup file
61 bundle create a changegroup file
62 cat output the current or given revision of files
62 cat output the current or given revision of files
63 clone make a copy of an existing repository
63 clone make a copy of an existing repository
64 commit commit the specified files or all outstanding changes
64 commit commit the specified files or all outstanding changes
65 config show combined config settings from all hgrc files
65 config show combined config settings from all hgrc files
66 copy mark files as copied for the next commit
66 copy mark files as copied for the next commit
67 diff diff repository (or selected files)
67 diff diff repository (or selected files)
68 export dump the header and diffs for one or more changesets
68 export dump the header and diffs for one or more changesets
69 files list tracked files
69 files list tracked files
70 forget forget the specified files on the next commit
70 forget forget the specified files on the next commit
71 graft copy changes from other branches onto the current branch
71 graft copy changes from other branches onto the current branch
72 grep search for a pattern in specified files and revisions
72 grep search for a pattern in specified files and revisions
73 heads show branch heads
73 heads show branch heads
74 help show help for a given topic or a help overview
74 help show help for a given topic or a help overview
75 identify identify the working directory or specified revision
75 identify identify the working directory or specified revision
76 import import an ordered set of patches
76 import import an ordered set of patches
77 incoming show new changesets found in source
77 incoming show new changesets found in source
78 init create a new repository in the given directory
78 init create a new repository in the given directory
79 log show revision history of entire repository or files
79 log show revision history of entire repository or files
80 manifest output the current or given revision of the project manifest
80 manifest output the current or given revision of the project manifest
81 merge merge another revision into working directory
81 merge merge another revision into working directory
82 outgoing show changesets not found in the destination
82 outgoing show changesets not found in the destination
83 paths show aliases for remote repositories
83 paths show aliases for remote repositories
84 phase set or show the current phase name
84 phase set or show the current phase name
85 pull pull changes from the specified source
85 pull pull changes from the specified source
86 push push changes to the specified destination
86 push push changes to the specified destination
87 recover roll back an interrupted transaction
87 recover roll back an interrupted transaction
88 remove remove the specified files on the next commit
88 remove remove the specified files on the next commit
89 rename rename files; equivalent of copy + remove
89 rename rename files; equivalent of copy + remove
90 resolve redo merges or set/view the merge status of files
90 resolve redo merges or set/view the merge status of files
91 revert restore files to their checkout state
91 revert restore files to their checkout state
92 root print the root (top) of the current working directory
92 root print the root (top) of the current working directory
93 serve start stand-alone webserver
93 serve start stand-alone webserver
94 status show changed files in the working directory
94 status show changed files in the working directory
95 summary summarize working directory state
95 summary summarize working directory state
96 tag add one or more tags for the current or given revision
96 tag add one or more tags for the current or given revision
97 tags list repository tags
97 tags list repository tags
98 unbundle apply one or more changegroup files
98 unbundle apply one or more changegroup files
99 update update working directory (or switch revisions)
99 update update working directory (or switch revisions)
100 verify verify the integrity of the repository
100 verify verify the integrity of the repository
101 version output version and copyright information
101 version output version and copyright information
102
102
103 additional help topics:
103 additional help topics:
104
104
105 config Configuration Files
105 config Configuration Files
106 dates Date Formats
106 dates Date Formats
107 diffs Diff Formats
107 diffs Diff Formats
108 environment Environment Variables
108 environment Environment Variables
109 extensions Using Additional Features
109 extensions Using Additional Features
110 filesets Specifying File Sets
110 filesets Specifying File Sets
111 glossary Glossary
111 glossary Glossary
112 hgignore Syntax for Mercurial Ignore Files
112 hgignore Syntax for Mercurial Ignore Files
113 hgweb Configuring hgweb
113 hgweb Configuring hgweb
114 internals Technical implementation topics
114 internals Technical implementation topics
115 merge-tools Merge Tools
115 merge-tools Merge Tools
116 multirevs Specifying Multiple Revisions
116 multirevs Specifying Multiple Revisions
117 patterns File Name Patterns
117 patterns File Name Patterns
118 phases Working with Phases
118 phases Working with Phases
119 revisions Specifying Single Revisions
119 revisions Specifying Single Revisions
120 revsets Specifying Revision Sets
120 revsets Specifying Revision Sets
121 scripting Using Mercurial from scripts and automation
121 scripting Using Mercurial from scripts and automation
122 subrepos Subrepositories
122 subrepos Subrepositories
123 templating Template Usage
123 templating Template Usage
124 urls URL Paths
124 urls URL Paths
125
125
126 (use "hg help -v" to show built-in aliases and global options)
126 (use "hg help -v" to show built-in aliases and global options)
127
127
128 $ hg -q help
128 $ hg -q help
129 add add the specified files on the next commit
129 add add the specified files on the next commit
130 addremove add all new files, delete all missing files
130 addremove add all new files, delete all missing files
131 annotate show changeset information by line for each file
131 annotate show changeset information by line for each file
132 archive create an unversioned archive of a repository revision
132 archive create an unversioned archive of a repository revision
133 backout reverse effect of earlier changeset
133 backout reverse effect of earlier changeset
134 bisect subdivision search of changesets
134 bisect subdivision search of changesets
135 bookmarks create a new bookmark or list existing bookmarks
135 bookmarks create a new bookmark or list existing bookmarks
136 branch set or show the current branch name
136 branch set or show the current branch name
137 branches list repository named branches
137 branches list repository named branches
138 bundle create a changegroup file
138 bundle create a changegroup file
139 cat output the current or given revision of files
139 cat output the current or given revision of files
140 clone make a copy of an existing repository
140 clone make a copy of an existing repository
141 commit commit the specified files or all outstanding changes
141 commit commit the specified files or all outstanding changes
142 config show combined config settings from all hgrc files
142 config show combined config settings from all hgrc files
143 copy mark files as copied for the next commit
143 copy mark files as copied for the next commit
144 diff diff repository (or selected files)
144 diff diff repository (or selected files)
145 export dump the header and diffs for one or more changesets
145 export dump the header and diffs for one or more changesets
146 files list tracked files
146 files list tracked files
147 forget forget the specified files on the next commit
147 forget forget the specified files on the next commit
148 graft copy changes from other branches onto the current branch
148 graft copy changes from other branches onto the current branch
149 grep search for a pattern in specified files and revisions
149 grep search for a pattern in specified files and revisions
150 heads show branch heads
150 heads show branch heads
151 help show help for a given topic or a help overview
151 help show help for a given topic or a help overview
152 identify identify the working directory or specified revision
152 identify identify the working directory or specified revision
153 import import an ordered set of patches
153 import import an ordered set of patches
154 incoming show new changesets found in source
154 incoming show new changesets found in source
155 init create a new repository in the given directory
155 init create a new repository in the given directory
156 log show revision history of entire repository or files
156 log show revision history of entire repository or files
157 manifest output the current or given revision of the project manifest
157 manifest output the current or given revision of the project manifest
158 merge merge another revision into working directory
158 merge merge another revision into working directory
159 outgoing show changesets not found in the destination
159 outgoing show changesets not found in the destination
160 paths show aliases for remote repositories
160 paths show aliases for remote repositories
161 phase set or show the current phase name
161 phase set or show the current phase name
162 pull pull changes from the specified source
162 pull pull changes from the specified source
163 push push changes to the specified destination
163 push push changes to the specified destination
164 recover roll back an interrupted transaction
164 recover roll back an interrupted transaction
165 remove remove the specified files on the next commit
165 remove remove the specified files on the next commit
166 rename rename files; equivalent of copy + remove
166 rename rename files; equivalent of copy + remove
167 resolve redo merges or set/view the merge status of files
167 resolve redo merges or set/view the merge status of files
168 revert restore files to their checkout state
168 revert restore files to their checkout state
169 root print the root (top) of the current working directory
169 root print the root (top) of the current working directory
170 serve start stand-alone webserver
170 serve start stand-alone webserver
171 status show changed files in the working directory
171 status show changed files in the working directory
172 summary summarize working directory state
172 summary summarize working directory state
173 tag add one or more tags for the current or given revision
173 tag add one or more tags for the current or given revision
174 tags list repository tags
174 tags list repository tags
175 unbundle apply one or more changegroup files
175 unbundle apply one or more changegroup files
176 update update working directory (or switch revisions)
176 update update working directory (or switch revisions)
177 verify verify the integrity of the repository
177 verify verify the integrity of the repository
178 version output version and copyright information
178 version output version and copyright information
179
179
180 additional help topics:
180 additional help topics:
181
181
182 config Configuration Files
182 config Configuration Files
183 dates Date Formats
183 dates Date Formats
184 diffs Diff Formats
184 diffs Diff Formats
185 environment Environment Variables
185 environment Environment Variables
186 extensions Using Additional Features
186 extensions Using Additional Features
187 filesets Specifying File Sets
187 filesets Specifying File Sets
188 glossary Glossary
188 glossary Glossary
189 hgignore Syntax for Mercurial Ignore Files
189 hgignore Syntax for Mercurial Ignore Files
190 hgweb Configuring hgweb
190 hgweb Configuring hgweb
191 internals Technical implementation topics
191 internals Technical implementation topics
192 merge-tools Merge Tools
192 merge-tools Merge Tools
193 multirevs Specifying Multiple Revisions
193 multirevs Specifying Multiple Revisions
194 patterns File Name Patterns
194 patterns File Name Patterns
195 phases Working with Phases
195 phases Working with Phases
196 revisions Specifying Single Revisions
196 revisions Specifying Single Revisions
197 revsets Specifying Revision Sets
197 revsets Specifying Revision Sets
198 scripting Using Mercurial from scripts and automation
198 scripting Using Mercurial from scripts and automation
199 subrepos Subrepositories
199 subrepos Subrepositories
200 templating Template Usage
200 templating Template Usage
201 urls URL Paths
201 urls URL Paths
202
202
203 Test extension help:
203 Test extension help:
204 $ hg help extensions --config extensions.rebase= --config extensions.children=
204 $ hg help extensions --config extensions.rebase= --config extensions.children=
205 Using Additional Features
205 Using Additional Features
206 """""""""""""""""""""""""
206 """""""""""""""""""""""""
207
207
208 Mercurial has the ability to add new features through the use of
208 Mercurial has the ability to add new features through the use of
209 extensions. Extensions may add new commands, add options to existing
209 extensions. Extensions may add new commands, add options to existing
210 commands, change the default behavior of commands, or implement hooks.
210 commands, change the default behavior of commands, or implement hooks.
211
211
212 To enable the "foo" extension, either shipped with Mercurial or in the
212 To enable the "foo" extension, either shipped with Mercurial or in the
213 Python search path, create an entry for it in your configuration file,
213 Python search path, create an entry for it in your configuration file,
214 like this:
214 like this:
215
215
216 [extensions]
216 [extensions]
217 foo =
217 foo =
218
218
219 You may also specify the full path to an extension:
219 You may also specify the full path to an extension:
220
220
221 [extensions]
221 [extensions]
222 myfeature = ~/.hgext/myfeature.py
222 myfeature = ~/.hgext/myfeature.py
223
223
224 See "hg help config" for more information on configuration files.
224 See "hg help config" for more information on configuration files.
225
225
226 Extensions are not loaded by default for a variety of reasons: they can
226 Extensions are not loaded by default for a variety of reasons: they can
227 increase startup overhead; they may be meant for advanced usage only; they
227 increase startup overhead; they may be meant for advanced usage only; they
228 may provide potentially dangerous abilities (such as letting you destroy
228 may provide potentially dangerous abilities (such as letting you destroy
229 or modify history); they might not be ready for prime time; or they may
229 or modify history); they might not be ready for prime time; or they may
230 alter some usual behaviors of stock Mercurial. It is thus up to the user
230 alter some usual behaviors of stock Mercurial. It is thus up to the user
231 to activate extensions as needed.
231 to activate extensions as needed.
232
232
233 To explicitly disable an extension enabled in a configuration file of
233 To explicitly disable an extension enabled in a configuration file of
234 broader scope, prepend its path with !:
234 broader scope, prepend its path with !:
235
235
236 [extensions]
236 [extensions]
237 # disabling extension bar residing in /path/to/extension/bar.py
237 # disabling extension bar residing in /path/to/extension/bar.py
238 bar = !/path/to/extension/bar.py
238 bar = !/path/to/extension/bar.py
239 # ditto, but no path was supplied for extension baz
239 # ditto, but no path was supplied for extension baz
240 baz = !
240 baz = !
241
241
242 enabled extensions:
242 enabled extensions:
243
243
244 children command to display child changesets (DEPRECATED)
244 children command to display child changesets (DEPRECATED)
245 rebase command to move sets of revisions to a different ancestor
245 rebase command to move sets of revisions to a different ancestor
246
246
247 disabled extensions:
247 disabled extensions:
248
248
249 acl hooks for controlling repository access
249 acl hooks for controlling repository access
250 blackbox log repository events to a blackbox for debugging
250 blackbox log repository events to a blackbox for debugging
251 bugzilla hooks for integrating with the Bugzilla bug tracker
251 bugzilla hooks for integrating with the Bugzilla bug tracker
252 censor erase file content at a given revision
252 censor erase file content at a given revision
253 churn command to display statistics about repository history
253 churn command to display statistics about repository history
254 clonebundles advertise pre-generated bundles to seed clones
254 clonebundles advertise pre-generated bundles to seed clones
255 (experimental)
255 (experimental)
256 color colorize output from some commands
256 color colorize output from some commands
257 convert import revisions from foreign VCS repositories into
257 convert import revisions from foreign VCS repositories into
258 Mercurial
258 Mercurial
259 eol automatically manage newlines in repository files
259 eol automatically manage newlines in repository files
260 extdiff command to allow external programs to compare revisions
260 extdiff command to allow external programs to compare revisions
261 factotum http authentication with factotum
261 factotum http authentication with factotum
262 gpg commands to sign and verify changesets
262 gpg commands to sign and verify changesets
263 hgcia hooks for integrating with the CIA.vc notification service
263 hgcia hooks for integrating with the CIA.vc notification service
264 hgk browse the repository in a graphical way
264 hgk browse the repository in a graphical way
265 highlight syntax highlighting for hgweb (requires Pygments)
265 highlight syntax highlighting for hgweb (requires Pygments)
266 histedit interactive history editing
266 histedit interactive history editing
267 keyword expand keywords in tracked files
267 keyword expand keywords in tracked files
268 largefiles track large binary files
268 largefiles track large binary files
269 mq manage a stack of patches
269 mq manage a stack of patches
270 notify hooks for sending email push notifications
270 notify hooks for sending email push notifications
271 pager browse command output with an external pager
271 pager browse command output with an external pager
272 patchbomb command to send changesets as (a series of) patch emails
272 patchbomb command to send changesets as (a series of) patch emails
273 purge command to delete untracked files from the working
273 purge command to delete untracked files from the working
274 directory
274 directory
275 record commands to interactively select changes for
275 record commands to interactively select changes for
276 commit/qrefresh
276 commit/qrefresh
277 relink recreates hardlinks between repository clones
277 relink recreates hardlinks between repository clones
278 schemes extend schemes with shortcuts to repository swarms
278 schemes extend schemes with shortcuts to repository swarms
279 share share a common history between several working directories
279 share share a common history between several working directories
280 shelve save and restore changes to the working directory
280 shelve save and restore changes to the working directory
281 strip strip changesets and their descendants from history
281 strip strip changesets and their descendants from history
282 transplant command to transplant changesets from another branch
282 transplant command to transplant changesets from another branch
283 win32mbcs allow the use of MBCS paths with problematic encodings
283 win32mbcs allow the use of MBCS paths with problematic encodings
284 zeroconf discover and advertise repositories on the local network
284 zeroconf discover and advertise repositories on the local network
285
285
286 Verify that extension keywords appear in help templates
286 Verify that extension keywords appear in help templates
287
287
288 $ hg help --config extensions.transplant= templating|grep transplant > /dev/null
288 $ hg help --config extensions.transplant= templating|grep transplant > /dev/null
289
289
290 Test short command list with verbose option
290 Test short command list with verbose option
291
291
292 $ hg -v help shortlist
292 $ hg -v help shortlist
293 Mercurial Distributed SCM
293 Mercurial Distributed SCM
294
294
295 basic commands:
295 basic commands:
296
296
297 add add the specified files on the next commit
297 add add the specified files on the next commit
298 annotate, blame
298 annotate, blame
299 show changeset information by line for each file
299 show changeset information by line for each file
300 clone make a copy of an existing repository
300 clone make a copy of an existing repository
301 commit, ci commit the specified files or all outstanding changes
301 commit, ci commit the specified files or all outstanding changes
302 diff diff repository (or selected files)
302 diff diff repository (or selected files)
303 export dump the header and diffs for one or more changesets
303 export dump the header and diffs for one or more changesets
304 forget forget the specified files on the next commit
304 forget forget the specified files on the next commit
305 init create a new repository in the given directory
305 init create a new repository in the given directory
306 log, history show revision history of entire repository or files
306 log, history show revision history of entire repository or files
307 merge merge another revision into working directory
307 merge merge another revision into working directory
308 pull pull changes from the specified source
308 pull pull changes from the specified source
309 push push changes to the specified destination
309 push push changes to the specified destination
310 remove, rm remove the specified files on the next commit
310 remove, rm remove the specified files on the next commit
311 serve start stand-alone webserver
311 serve start stand-alone webserver
312 status, st show changed files in the working directory
312 status, st show changed files in the working directory
313 summary, sum summarize working directory state
313 summary, sum summarize working directory state
314 update, up, checkout, co
314 update, up, checkout, co
315 update working directory (or switch revisions)
315 update working directory (or switch revisions)
316
316
317 global options ([+] can be repeated):
317 global options ([+] can be repeated):
318
318
319 -R --repository REPO repository root directory or name of overlay bundle
319 -R --repository REPO repository root directory or name of overlay bundle
320 file
320 file
321 --cwd DIR change working directory
321 --cwd DIR change working directory
322 -y --noninteractive do not prompt, automatically pick the first choice for
322 -y --noninteractive do not prompt, automatically pick the first choice for
323 all prompts
323 all prompts
324 -q --quiet suppress output
324 -q --quiet suppress output
325 -v --verbose enable additional output
325 -v --verbose enable additional output
326 --config CONFIG [+] set/override config option (use 'section.name=value')
326 --config CONFIG [+] set/override config option (use 'section.name=value')
327 --debug enable debugging output
327 --debug enable debugging output
328 --debugger start debugger
328 --debugger start debugger
329 --encoding ENCODE set the charset encoding (default: ascii)
329 --encoding ENCODE set the charset encoding (default: ascii)
330 --encodingmode MODE set the charset encoding mode (default: strict)
330 --encodingmode MODE set the charset encoding mode (default: strict)
331 --traceback always print a traceback on exception
331 --traceback always print a traceback on exception
332 --time time how long the command takes
332 --time time how long the command takes
333 --profile print command execution profile
333 --profile print command execution profile
334 --version output version information and exit
334 --version output version information and exit
335 -h --help display help and exit
335 -h --help display help and exit
336 --hidden consider hidden changesets
336 --hidden consider hidden changesets
337
337
338 (use "hg help" for the full list of commands)
338 (use "hg help" for the full list of commands)
339
339
340 $ hg add -h
340 $ hg add -h
341 hg add [OPTION]... [FILE]...
341 hg add [OPTION]... [FILE]...
342
342
343 add the specified files on the next commit
343 add the specified files on the next commit
344
344
345 Schedule files to be version controlled and added to the repository.
345 Schedule files to be version controlled and added to the repository.
346
346
347 The files will be added to the repository at the next commit. To undo an
347 The files will be added to the repository at the next commit. To undo an
348 add before that, see "hg forget".
348 add before that, see "hg forget".
349
349
350 If no names are given, add all files to the repository (except files
350 If no names are given, add all files to the repository (except files
351 matching ".hgignore").
351 matching ".hgignore").
352
352
353 Returns 0 if all files are successfully added.
353 Returns 0 if all files are successfully added.
354
354
355 options ([+] can be repeated):
355 options ([+] can be repeated):
356
356
357 -I --include PATTERN [+] include names matching the given patterns
357 -I --include PATTERN [+] include names matching the given patterns
358 -X --exclude PATTERN [+] exclude names matching the given patterns
358 -X --exclude PATTERN [+] exclude names matching the given patterns
359 -S --subrepos recurse into subrepositories
359 -S --subrepos recurse into subrepositories
360 -n --dry-run do not perform actions, just print output
360 -n --dry-run do not perform actions, just print output
361
361
362 (some details hidden, use --verbose to show complete help)
362 (some details hidden, use --verbose to show complete help)
363
363
364 Verbose help for add
364 Verbose help for add
365
365
366 $ hg add -hv
366 $ hg add -hv
367 hg add [OPTION]... [FILE]...
367 hg add [OPTION]... [FILE]...
368
368
369 add the specified files on the next commit
369 add the specified files on the next commit
370
370
371 Schedule files to be version controlled and added to the repository.
371 Schedule files to be version controlled and added to the repository.
372
372
373 The files will be added to the repository at the next commit. To undo an
373 The files will be added to the repository at the next commit. To undo an
374 add before that, see "hg forget".
374 add before that, see "hg forget".
375
375
376 If no names are given, add all files to the repository (except files
376 If no names are given, add all files to the repository (except files
377 matching ".hgignore").
377 matching ".hgignore").
378
378
379 Examples:
379 Examples:
380
380
381 - New (unknown) files are added automatically by "hg add":
381 - New (unknown) files are added automatically by "hg add":
382
382
383 $ ls
383 $ ls
384 foo.c
384 foo.c
385 $ hg status
385 $ hg status
386 ? foo.c
386 ? foo.c
387 $ hg add
387 $ hg add
388 adding foo.c
388 adding foo.c
389 $ hg status
389 $ hg status
390 A foo.c
390 A foo.c
391
391
392 - Specific files to be added can be specified:
392 - Specific files to be added can be specified:
393
393
394 $ ls
394 $ ls
395 bar.c foo.c
395 bar.c foo.c
396 $ hg status
396 $ hg status
397 ? bar.c
397 ? bar.c
398 ? foo.c
398 ? foo.c
399 $ hg add bar.c
399 $ hg add bar.c
400 $ hg status
400 $ hg status
401 A bar.c
401 A bar.c
402 ? foo.c
402 ? foo.c
403
403
404 Returns 0 if all files are successfully added.
404 Returns 0 if all files are successfully added.
405
405
406 options ([+] can be repeated):
406 options ([+] can be repeated):
407
407
408 -I --include PATTERN [+] include names matching the given patterns
408 -I --include PATTERN [+] include names matching the given patterns
409 -X --exclude PATTERN [+] exclude names matching the given patterns
409 -X --exclude PATTERN [+] exclude names matching the given patterns
410 -S --subrepos recurse into subrepositories
410 -S --subrepos recurse into subrepositories
411 -n --dry-run do not perform actions, just print output
411 -n --dry-run do not perform actions, just print output
412
412
413 global options ([+] can be repeated):
413 global options ([+] can be repeated):
414
414
415 -R --repository REPO repository root directory or name of overlay bundle
415 -R --repository REPO repository root directory or name of overlay bundle
416 file
416 file
417 --cwd DIR change working directory
417 --cwd DIR change working directory
418 -y --noninteractive do not prompt, automatically pick the first choice for
418 -y --noninteractive do not prompt, automatically pick the first choice for
419 all prompts
419 all prompts
420 -q --quiet suppress output
420 -q --quiet suppress output
421 -v --verbose enable additional output
421 -v --verbose enable additional output
422 --config CONFIG [+] set/override config option (use 'section.name=value')
422 --config CONFIG [+] set/override config option (use 'section.name=value')
423 --debug enable debugging output
423 --debug enable debugging output
424 --debugger start debugger
424 --debugger start debugger
425 --encoding ENCODE set the charset encoding (default: ascii)
425 --encoding ENCODE set the charset encoding (default: ascii)
426 --encodingmode MODE set the charset encoding mode (default: strict)
426 --encodingmode MODE set the charset encoding mode (default: strict)
427 --traceback always print a traceback on exception
427 --traceback always print a traceback on exception
428 --time time how long the command takes
428 --time time how long the command takes
429 --profile print command execution profile
429 --profile print command execution profile
430 --version output version information and exit
430 --version output version information and exit
431 -h --help display help and exit
431 -h --help display help and exit
432 --hidden consider hidden changesets
432 --hidden consider hidden changesets
433
433
434 Test help option with version option
434 Test help option with version option
435
435
436 $ hg add -h --version
436 $ hg add -h --version
437 Mercurial Distributed SCM (version *) (glob)
437 Mercurial Distributed SCM (version *) (glob)
438 (see https://mercurial-scm.org for more information)
438 (see https://mercurial-scm.org for more information)
439
439
440 Copyright (C) 2005-2015 Matt Mackall and others
440 Copyright (C) 2005-2015 Matt Mackall and others
441 This is free software; see the source for copying conditions. There is NO
441 This is free software; see the source for copying conditions. There is NO
442 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
442 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
443
443
444 $ hg add --skjdfks
444 $ hg add --skjdfks
445 hg add: option --skjdfks not recognized
445 hg add: option --skjdfks not recognized
446 hg add [OPTION]... [FILE]...
446 hg add [OPTION]... [FILE]...
447
447
448 add the specified files on the next commit
448 add the specified files on the next commit
449
449
450 options ([+] can be repeated):
450 options ([+] can be repeated):
451
451
452 -I --include PATTERN [+] include names matching the given patterns
452 -I --include PATTERN [+] include names matching the given patterns
453 -X --exclude PATTERN [+] exclude names matching the given patterns
453 -X --exclude PATTERN [+] exclude names matching the given patterns
454 -S --subrepos recurse into subrepositories
454 -S --subrepos recurse into subrepositories
455 -n --dry-run do not perform actions, just print output
455 -n --dry-run do not perform actions, just print output
456
456
457 (use "hg add -h" to show more help)
457 (use "hg add -h" to show more help)
458 [255]
458 [255]
459
459
460 Test ambiguous command help
460 Test ambiguous command help
461
461
462 $ hg help ad
462 $ hg help ad
463 list of commands:
463 list of commands:
464
464
465 add add the specified files on the next commit
465 add add the specified files on the next commit
466 addremove add all new files, delete all missing files
466 addremove add all new files, delete all missing files
467
467
468 (use "hg help -v ad" to show built-in aliases and global options)
468 (use "hg help -v ad" to show built-in aliases and global options)
469
469
470 Test command without options
470 Test command without options
471
471
472 $ hg help verify
472 $ hg help verify
473 hg verify
473 hg verify
474
474
475 verify the integrity of the repository
475 verify the integrity of the repository
476
476
477 Verify the integrity of the current repository.
477 Verify the integrity of the current repository.
478
478
479 This will perform an extensive check of the repository's integrity,
479 This will perform an extensive check of the repository's integrity,
480 validating the hashes and checksums of each entry in the changelog,
480 validating the hashes and checksums of each entry in the changelog,
481 manifest, and tracked files, as well as the integrity of their crosslinks
481 manifest, and tracked files, as well as the integrity of their crosslinks
482 and indices.
482 and indices.
483
483
484 Please see https://mercurial-scm.org/wiki/RepositoryCorruption for more
484 Please see https://mercurial-scm.org/wiki/RepositoryCorruption for more
485 information about recovery from corruption of the repository.
485 information about recovery from corruption of the repository.
486
486
487 Returns 0 on success, 1 if errors are encountered.
487 Returns 0 on success, 1 if errors are encountered.
488
488
489 (some details hidden, use --verbose to show complete help)
489 (some details hidden, use --verbose to show complete help)
490
490
491 $ hg help diff
491 $ hg help diff
492 hg diff [OPTION]... ([-c REV] | [-r REV1 [-r REV2]]) [FILE]...
492 hg diff [OPTION]... ([-c REV] | [-r REV1 [-r REV2]]) [FILE]...
493
493
494 diff repository (or selected files)
494 diff repository (or selected files)
495
495
496 Show differences between revisions for the specified files.
496 Show differences between revisions for the specified files.
497
497
498 Differences between files are shown using the unified diff format.
498 Differences between files are shown using the unified diff format.
499
499
500 Note:
500 Note:
501 "hg diff" may generate unexpected results for merges, as it will
501 "hg diff" may generate unexpected results for merges, as it will
502 default to comparing against the working directory's first parent
502 default to comparing against the working directory's first parent
503 changeset if no revisions are specified.
503 changeset if no revisions are specified.
504
504
505 When two revision arguments are given, then changes are shown between
505 When two revision arguments are given, then changes are shown between
506 those revisions. If only one revision is specified then that revision is
506 those revisions. If only one revision is specified then that revision is
507 compared to the working directory, and, when no revisions are specified,
507 compared to the working directory, and, when no revisions are specified,
508 the working directory files are compared to its first parent.
508 the working directory files are compared to its first parent.
509
509
510 Alternatively you can specify -c/--change with a revision to see the
510 Alternatively you can specify -c/--change with a revision to see the
511 changes in that changeset relative to its first parent.
511 changes in that changeset relative to its first parent.
512
512
513 Without the -a/--text option, diff will avoid generating diffs of files it
513 Without the -a/--text option, diff will avoid generating diffs of files it
514 detects as binary. With -a, diff will generate a diff anyway, probably
514 detects as binary. With -a, diff will generate a diff anyway, probably
515 with undesirable results.
515 with undesirable results.
516
516
517 Use the -g/--git option to generate diffs in the git extended diff format.
517 Use the -g/--git option to generate diffs in the git extended diff format.
518 For more information, read "hg help diffs".
518 For more information, read "hg help diffs".
519
519
520 Returns 0 on success.
520 Returns 0 on success.
521
521
522 options ([+] can be repeated):
522 options ([+] can be repeated):
523
523
524 -r --rev REV [+] revision
524 -r --rev REV [+] revision
525 -c --change REV change made by revision
525 -c --change REV change made by revision
526 -a --text treat all files as text
526 -a --text treat all files as text
527 -g --git use git extended diff format
527 -g --git use git extended diff format
528 --nodates omit dates from diff headers
528 --nodates omit dates from diff headers
529 --noprefix omit a/ and b/ prefixes from filenames
529 --noprefix omit a/ and b/ prefixes from filenames
530 -p --show-function show which function each change is in
530 -p --show-function show which function each change is in
531 --reverse produce a diff that undoes the changes
531 --reverse produce a diff that undoes the changes
532 -w --ignore-all-space ignore white space when comparing lines
532 -w --ignore-all-space ignore white space when comparing lines
533 -b --ignore-space-change ignore changes in the amount of white space
533 -b --ignore-space-change ignore changes in the amount of white space
534 -B --ignore-blank-lines ignore changes whose lines are all blank
534 -B --ignore-blank-lines ignore changes whose lines are all blank
535 -U --unified NUM number of lines of context to show
535 -U --unified NUM number of lines of context to show
536 --stat output diffstat-style summary of changes
536 --stat output diffstat-style summary of changes
537 --root DIR produce diffs relative to subdirectory
537 --root DIR produce diffs relative to subdirectory
538 -I --include PATTERN [+] include names matching the given patterns
538 -I --include PATTERN [+] include names matching the given patterns
539 -X --exclude PATTERN [+] exclude names matching the given patterns
539 -X --exclude PATTERN [+] exclude names matching the given patterns
540 -S --subrepos recurse into subrepositories
540 -S --subrepos recurse into subrepositories
541
541
542 (some details hidden, use --verbose to show complete help)
542 (some details hidden, use --verbose to show complete help)
543
543
544 $ hg help status
544 $ hg help status
545 hg status [OPTION]... [FILE]...
545 hg status [OPTION]... [FILE]...
546
546
547 aliases: st
547 aliases: st
548
548
549 show changed files in the working directory
549 show changed files in the working directory
550
550
551 Show status of files in the repository. If names are given, only files
551 Show status of files in the repository. If names are given, only files
552 that match are shown. Files that are clean or ignored or the source of a
552 that match are shown. Files that are clean or ignored or the source of a
553 copy/move operation, are not listed unless -c/--clean, -i/--ignored,
553 copy/move operation, are not listed unless -c/--clean, -i/--ignored,
554 -C/--copies or -A/--all are given. Unless options described with "show
554 -C/--copies or -A/--all are given. Unless options described with "show
555 only ..." are given, the options -mardu are used.
555 only ..." are given, the options -mardu are used.
556
556
557 Option -q/--quiet hides untracked (unknown and ignored) files unless
557 Option -q/--quiet hides untracked (unknown and ignored) files unless
558 explicitly requested with -u/--unknown or -i/--ignored.
558 explicitly requested with -u/--unknown or -i/--ignored.
559
559
560 Note:
560 Note:
561 "hg status" may appear to disagree with diff if permissions have
561 "hg status" may appear to disagree with diff if permissions have
562 changed or a merge has occurred. The standard diff format does not
562 changed or a merge has occurred. The standard diff format does not
563 report permission changes and diff only reports changes relative to one
563 report permission changes and diff only reports changes relative to one
564 merge parent.
564 merge parent.
565
565
566 If one revision is given, it is used as the base revision. If two
566 If one revision is given, it is used as the base revision. If two
567 revisions are given, the differences between them are shown. The --change
567 revisions are given, the differences between them are shown. The --change
568 option can also be used as a shortcut to list the changed files of a
568 option can also be used as a shortcut to list the changed files of a
569 revision from its first parent.
569 revision from its first parent.
570
570
571 The codes used to show the status of files are:
571 The codes used to show the status of files are:
572
572
573 M = modified
573 M = modified
574 A = added
574 A = added
575 R = removed
575 R = removed
576 C = clean
576 C = clean
577 ! = missing (deleted by non-hg command, but still tracked)
577 ! = missing (deleted by non-hg command, but still tracked)
578 ? = not tracked
578 ? = not tracked
579 I = ignored
579 I = ignored
580 = origin of the previous file (with --copies)
580 = origin of the previous file (with --copies)
581
581
582 Returns 0 on success.
582 Returns 0 on success.
583
583
584 options ([+] can be repeated):
584 options ([+] can be repeated):
585
585
586 -A --all show status of all files
586 -A --all show status of all files
587 -m --modified show only modified files
587 -m --modified show only modified files
588 -a --added show only added files
588 -a --added show only added files
589 -r --removed show only removed files
589 -r --removed show only removed files
590 -d --deleted show only deleted (but tracked) files
590 -d --deleted show only deleted (but tracked) files
591 -c --clean show only files without changes
591 -c --clean show only files without changes
592 -u --unknown show only unknown (not tracked) files
592 -u --unknown show only unknown (not tracked) files
593 -i --ignored show only ignored files
593 -i --ignored show only ignored files
594 -n --no-status hide status prefix
594 -n --no-status hide status prefix
595 -C --copies show source of copied files
595 -C --copies show source of copied files
596 -0 --print0 end filenames with NUL, for use with xargs
596 -0 --print0 end filenames with NUL, for use with xargs
597 --rev REV [+] show difference from revision
597 --rev REV [+] show difference from revision
598 --change REV list the changed files of a revision
598 --change REV list the changed files of a revision
599 -I --include PATTERN [+] include names matching the given patterns
599 -I --include PATTERN [+] include names matching the given patterns
600 -X --exclude PATTERN [+] exclude names matching the given patterns
600 -X --exclude PATTERN [+] exclude names matching the given patterns
601 -S --subrepos recurse into subrepositories
601 -S --subrepos recurse into subrepositories
602
602
603 (some details hidden, use --verbose to show complete help)
603 (some details hidden, use --verbose to show complete help)
604
604
605 $ hg -q help status
605 $ hg -q help status
606 hg status [OPTION]... [FILE]...
606 hg status [OPTION]... [FILE]...
607
607
608 show changed files in the working directory
608 show changed files in the working directory
609
609
610 $ hg help foo
610 $ hg help foo
611 abort: no such help topic: foo
611 abort: no such help topic: foo
612 (try "hg help --keyword foo")
612 (try "hg help --keyword foo")
613 [255]
613 [255]
614
614
615 $ hg skjdfks
615 $ hg skjdfks
616 hg: unknown command 'skjdfks'
616 hg: unknown command 'skjdfks'
617 Mercurial Distributed SCM
617 Mercurial Distributed SCM
618
618
619 basic commands:
619 basic commands:
620
620
621 add add the specified files on the next commit
621 add add the specified files on the next commit
622 annotate show changeset information by line for each file
622 annotate show changeset information by line for each file
623 clone make a copy of an existing repository
623 clone make a copy of an existing repository
624 commit commit the specified files or all outstanding changes
624 commit commit the specified files or all outstanding changes
625 diff diff repository (or selected files)
625 diff diff repository (or selected files)
626 export dump the header and diffs for one or more changesets
626 export dump the header and diffs for one or more changesets
627 forget forget the specified files on the next commit
627 forget forget the specified files on the next commit
628 init create a new repository in the given directory
628 init create a new repository in the given directory
629 log show revision history of entire repository or files
629 log show revision history of entire repository or files
630 merge merge another revision into working directory
630 merge merge another revision into working directory
631 pull pull changes from the specified source
631 pull pull changes from the specified source
632 push push changes to the specified destination
632 push push changes to the specified destination
633 remove remove the specified files on the next commit
633 remove remove the specified files on the next commit
634 serve start stand-alone webserver
634 serve start stand-alone webserver
635 status show changed files in the working directory
635 status show changed files in the working directory
636 summary summarize working directory state
636 summary summarize working directory state
637 update update working directory (or switch revisions)
637 update update working directory (or switch revisions)
638
638
639 (use "hg help" for the full list of commands or "hg -v" for details)
639 (use "hg help" for the full list of commands or "hg -v" for details)
640 [255]
640 [255]
641
641
642
642
643 Make sure that we don't run afoul of the help system thinking that
643 Make sure that we don't run afoul of the help system thinking that
644 this is a section and erroring out weirdly.
644 this is a section and erroring out weirdly.
645
645
646 $ hg .log
646 $ hg .log
647 hg: unknown command '.log'
647 hg: unknown command '.log'
648 (did you mean log?)
648 (did you mean log?)
649 [255]
649 [255]
650
650
651 $ hg log.
651 $ hg log.
652 hg: unknown command 'log.'
652 hg: unknown command 'log.'
653 (did you mean log?)
653 (did you mean log?)
654 [255]
654 [255]
655 $ hg pu.lh
655 $ hg pu.lh
656 hg: unknown command 'pu.lh'
656 hg: unknown command 'pu.lh'
657 (did you mean one of pull, push?)
657 (did you mean one of pull, push?)
658 [255]
658 [255]
659
659
660 $ cat > helpext.py <<EOF
660 $ cat > helpext.py <<EOF
661 > import os
661 > import os
662 > from mercurial import cmdutil, commands
662 > from mercurial import cmdutil, commands
663 >
663 >
664 > cmdtable = {}
664 > cmdtable = {}
665 > command = cmdutil.command(cmdtable)
665 > command = cmdutil.command(cmdtable)
666 >
666 >
667 > @command('nohelp',
667 > @command('nohelp',
668 > [('', 'longdesc', 3, 'x'*90),
668 > [('', 'longdesc', 3, 'x'*90),
669 > ('n', '', None, 'normal desc'),
669 > ('n', '', None, 'normal desc'),
670 > ('', 'newline', '', 'line1\nline2')],
670 > ('', 'newline', '', 'line1\nline2')],
671 > 'hg nohelp',
671 > 'hg nohelp',
672 > norepo=True)
672 > norepo=True)
673 > @command('debugoptDEP', [('', 'dopt', None, 'option is (DEPRECATED)')])
673 > @command('debugoptDEP', [('', 'dopt', None, 'option is (DEPRECATED)')])
674 > @command('debugoptEXP', [('', 'eopt', None, 'option is (EXPERIMENTAL)')])
674 > @command('debugoptEXP', [('', 'eopt', None, 'option is (EXPERIMENTAL)')])
675 > def nohelp(ui, *args, **kwargs):
675 > def nohelp(ui, *args, **kwargs):
676 > pass
676 > pass
677 >
677 >
678 > EOF
678 > EOF
679 $ echo '[extensions]' >> $HGRCPATH
679 $ echo '[extensions]' >> $HGRCPATH
680 $ echo "helpext = `pwd`/helpext.py" >> $HGRCPATH
680 $ echo "helpext = `pwd`/helpext.py" >> $HGRCPATH
681
681
682 Test command with no help text
682 Test command with no help text
683
683
684 $ hg help nohelp
684 $ hg help nohelp
685 hg nohelp
685 hg nohelp
686
686
687 (no help text available)
687 (no help text available)
688
688
689 options:
689 options:
690
690
691 --longdesc VALUE xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
691 --longdesc VALUE xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
692 xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx (default: 3)
692 xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx (default: 3)
693 -n -- normal desc
693 -n -- normal desc
694 --newline VALUE line1 line2
694 --newline VALUE line1 line2
695
695
696 (some details hidden, use --verbose to show complete help)
696 (some details hidden, use --verbose to show complete help)
697
697
698 $ hg help -k nohelp
698 $ hg help -k nohelp
699 Commands:
699 Commands:
700
700
701 nohelp hg nohelp
701 nohelp hg nohelp
702
702
703 Extension Commands:
703 Extension Commands:
704
704
705 nohelp (no help text available)
705 nohelp (no help text available)
706
706
707 Test that default list of commands omits extension commands
707 Test that default list of commands omits extension commands
708
708
709 $ hg help
709 $ hg help
710 Mercurial Distributed SCM
710 Mercurial Distributed SCM
711
711
712 list of commands:
712 list of commands:
713
713
714 add add the specified files on the next commit
714 add add the specified files on the next commit
715 addremove add all new files, delete all missing files
715 addremove add all new files, delete all missing files
716 annotate show changeset information by line for each file
716 annotate show changeset information by line for each file
717 archive create an unversioned archive of a repository revision
717 archive create an unversioned archive of a repository revision
718 backout reverse effect of earlier changeset
718 backout reverse effect of earlier changeset
719 bisect subdivision search of changesets
719 bisect subdivision search of changesets
720 bookmarks create a new bookmark or list existing bookmarks
720 bookmarks create a new bookmark or list existing bookmarks
721 branch set or show the current branch name
721 branch set or show the current branch name
722 branches list repository named branches
722 branches list repository named branches
723 bundle create a changegroup file
723 bundle create a changegroup file
724 cat output the current or given revision of files
724 cat output the current or given revision of files
725 clone make a copy of an existing repository
725 clone make a copy of an existing repository
726 commit commit the specified files or all outstanding changes
726 commit commit the specified files or all outstanding changes
727 config show combined config settings from all hgrc files
727 config show combined config settings from all hgrc files
728 copy mark files as copied for the next commit
728 copy mark files as copied for the next commit
729 diff diff repository (or selected files)
729 diff diff repository (or selected files)
730 export dump the header and diffs for one or more changesets
730 export dump the header and diffs for one or more changesets
731 files list tracked files
731 files list tracked files
732 forget forget the specified files on the next commit
732 forget forget the specified files on the next commit
733 graft copy changes from other branches onto the current branch
733 graft copy changes from other branches onto the current branch
734 grep search for a pattern in specified files and revisions
734 grep search for a pattern in specified files and revisions
735 heads show branch heads
735 heads show branch heads
736 help show help for a given topic or a help overview
736 help show help for a given topic or a help overview
737 identify identify the working directory or specified revision
737 identify identify the working directory or specified revision
738 import import an ordered set of patches
738 import import an ordered set of patches
739 incoming show new changesets found in source
739 incoming show new changesets found in source
740 init create a new repository in the given directory
740 init create a new repository in the given directory
741 log show revision history of entire repository or files
741 log show revision history of entire repository or files
742 manifest output the current or given revision of the project manifest
742 manifest output the current or given revision of the project manifest
743 merge merge another revision into working directory
743 merge merge another revision into working directory
744 outgoing show changesets not found in the destination
744 outgoing show changesets not found in the destination
745 paths show aliases for remote repositories
745 paths show aliases for remote repositories
746 phase set or show the current phase name
746 phase set or show the current phase name
747 pull pull changes from the specified source
747 pull pull changes from the specified source
748 push push changes to the specified destination
748 push push changes to the specified destination
749 recover roll back an interrupted transaction
749 recover roll back an interrupted transaction
750 remove remove the specified files on the next commit
750 remove remove the specified files on the next commit
751 rename rename files; equivalent of copy + remove
751 rename rename files; equivalent of copy + remove
752 resolve redo merges or set/view the merge status of files
752 resolve redo merges or set/view the merge status of files
753 revert restore files to their checkout state
753 revert restore files to their checkout state
754 root print the root (top) of the current working directory
754 root print the root (top) of the current working directory
755 serve start stand-alone webserver
755 serve start stand-alone webserver
756 status show changed files in the working directory
756 status show changed files in the working directory
757 summary summarize working directory state
757 summary summarize working directory state
758 tag add one or more tags for the current or given revision
758 tag add one or more tags for the current or given revision
759 tags list repository tags
759 tags list repository tags
760 unbundle apply one or more changegroup files
760 unbundle apply one or more changegroup files
761 update update working directory (or switch revisions)
761 update update working directory (or switch revisions)
762 verify verify the integrity of the repository
762 verify verify the integrity of the repository
763 version output version and copyright information
763 version output version and copyright information
764
764
765 enabled extensions:
765 enabled extensions:
766
766
767 helpext (no help text available)
767 helpext (no help text available)
768
768
769 additional help topics:
769 additional help topics:
770
770
771 config Configuration Files
771 config Configuration Files
772 dates Date Formats
772 dates Date Formats
773 diffs Diff Formats
773 diffs Diff Formats
774 environment Environment Variables
774 environment Environment Variables
775 extensions Using Additional Features
775 extensions Using Additional Features
776 filesets Specifying File Sets
776 filesets Specifying File Sets
777 glossary Glossary
777 glossary Glossary
778 hgignore Syntax for Mercurial Ignore Files
778 hgignore Syntax for Mercurial Ignore Files
779 hgweb Configuring hgweb
779 hgweb Configuring hgweb
780 internals Technical implementation topics
780 internals Technical implementation topics
781 merge-tools Merge Tools
781 merge-tools Merge Tools
782 multirevs Specifying Multiple Revisions
782 multirevs Specifying Multiple Revisions
783 patterns File Name Patterns
783 patterns File Name Patterns
784 phases Working with Phases
784 phases Working with Phases
785 revisions Specifying Single Revisions
785 revisions Specifying Single Revisions
786 revsets Specifying Revision Sets
786 revsets Specifying Revision Sets
787 scripting Using Mercurial from scripts and automation
787 scripting Using Mercurial from scripts and automation
788 subrepos Subrepositories
788 subrepos Subrepositories
789 templating Template Usage
789 templating Template Usage
790 urls URL Paths
790 urls URL Paths
791
791
792 (use "hg help -v" to show built-in aliases and global options)
792 (use "hg help -v" to show built-in aliases and global options)
793
793
794
794
795 Test list of internal help commands
795 Test list of internal help commands
796
796
797 $ hg help debug
797 $ hg help debug
798 debug commands (internal and unsupported):
798 debug commands (internal and unsupported):
799
799
800 debugancestor
800 debugancestor
801 find the ancestor revision of two revisions in a given index
801 find the ancestor revision of two revisions in a given index
802 debugapplystreamclonebundle
802 debugapplystreamclonebundle
803 apply a stream clone bundle file
803 apply a stream clone bundle file
804 debugbuilddag
804 debugbuilddag
805 builds a repo with a given DAG from scratch in the current
805 builds a repo with a given DAG from scratch in the current
806 empty repo
806 empty repo
807 debugbundle lists the contents of a bundle
807 debugbundle lists the contents of a bundle
808 debugcheckstate
808 debugcheckstate
809 validate the correctness of the current dirstate
809 validate the correctness of the current dirstate
810 debugcommands
810 debugcommands
811 list all available commands and options
811 list all available commands and options
812 debugcomplete
812 debugcomplete
813 returns the completion list associated with the given command
813 returns the completion list associated with the given command
814 debugcreatestreamclonebundle
814 debugcreatestreamclonebundle
815 create a stream clone bundle file
815 create a stream clone bundle file
816 debugdag format the changelog or an index DAG as a concise textual
816 debugdag format the changelog or an index DAG as a concise textual
817 description
817 description
818 debugdata dump the contents of a data file revision
818 debugdata dump the contents of a data file revision
819 debugdate parse and display a date
819 debugdate parse and display a date
820 debugdeltachain
820 debugdeltachain
821 dump information about delta chains in a revlog
821 dump information about delta chains in a revlog
822 debugdirstate
822 debugdirstate
823 show the contents of the current dirstate
823 show the contents of the current dirstate
824 debugdiscovery
824 debugdiscovery
825 runs the changeset discovery protocol in isolation
825 runs the changeset discovery protocol in isolation
826 debugextensions
826 debugextensions
827 show information about active extensions
827 show information about active extensions
828 debugfileset parse and apply a fileset specification
828 debugfileset parse and apply a fileset specification
829 debugfsinfo show information detected about current filesystem
829 debugfsinfo show information detected about current filesystem
830 debuggetbundle
830 debuggetbundle
831 retrieves a bundle from a repo
831 retrieves a bundle from a repo
832 debugignore display the combined ignore pattern
832 debugignore display the combined ignore pattern and information about
833 ignored files
833 debugindex dump the contents of an index file
834 debugindex dump the contents of an index file
834 debugindexdot
835 debugindexdot
835 dump an index DAG as a graphviz dot file
836 dump an index DAG as a graphviz dot file
836 debuginstall test Mercurial installation
837 debuginstall test Mercurial installation
837 debugknown test whether node ids are known to a repo
838 debugknown test whether node ids are known to a repo
838 debuglocks show or modify state of locks
839 debuglocks show or modify state of locks
839 debugmergestate
840 debugmergestate
840 print merge state
841 print merge state
841 debugnamecomplete
842 debugnamecomplete
842 complete "names" - tags, open branch names, bookmark names
843 complete "names" - tags, open branch names, bookmark names
843 debugobsolete
844 debugobsolete
844 create arbitrary obsolete marker
845 create arbitrary obsolete marker
845 debugoptDEP (no help text available)
846 debugoptDEP (no help text available)
846 debugoptEXP (no help text available)
847 debugoptEXP (no help text available)
847 debugpathcomplete
848 debugpathcomplete
848 complete part or all of a tracked path
849 complete part or all of a tracked path
849 debugpushkey access the pushkey key/value protocol
850 debugpushkey access the pushkey key/value protocol
850 debugpvec (no help text available)
851 debugpvec (no help text available)
851 debugrebuilddirstate
852 debugrebuilddirstate
852 rebuild the dirstate as it would look like for the given
853 rebuild the dirstate as it would look like for the given
853 revision
854 revision
854 debugrebuildfncache
855 debugrebuildfncache
855 rebuild the fncache file
856 rebuild the fncache file
856 debugrename dump rename information
857 debugrename dump rename information
857 debugrevlog show data and statistics about a revlog
858 debugrevlog show data and statistics about a revlog
858 debugrevspec parse and apply a revision specification
859 debugrevspec parse and apply a revision specification
859 debugsetparents
860 debugsetparents
860 manually set the parents of the current working directory
861 manually set the parents of the current working directory
861 debugsub (no help text available)
862 debugsub (no help text available)
862 debugsuccessorssets
863 debugsuccessorssets
863 show set of successors for revision
864 show set of successors for revision
864 debugwalk show how files match on given patterns
865 debugwalk show how files match on given patterns
865 debugwireargs
866 debugwireargs
866 (no help text available)
867 (no help text available)
867
868
868 (use "hg help -v debug" to show built-in aliases and global options)
869 (use "hg help -v debug" to show built-in aliases and global options)
869
870
870 internals topic renders index of available sub-topics
871 internals topic renders index of available sub-topics
871
872
872 $ hg help internals
873 $ hg help internals
873 Technical implementation topics
874 Technical implementation topics
874 """""""""""""""""""""""""""""""
875 """""""""""""""""""""""""""""""
875
876
876 bundles container for exchange of repository data
877 bundles container for exchange of repository data
877 changegroups representation of revlog data
878 changegroups representation of revlog data
878 revlogs revision storage mechanism
879 revlogs revision storage mechanism
879
880
880 sub-topics can be accessed
881 sub-topics can be accessed
881
882
882 $ hg help internals.changegroups
883 $ hg help internals.changegroups
883 Changegroups
884 Changegroups
884 ============
885 ============
885
886
886 Changegroups are representations of repository revlog data, specifically
887 Changegroups are representations of repository revlog data, specifically
887 the changelog, manifest, and filelogs.
888 the changelog, manifest, and filelogs.
888
889
889 There are 3 versions of changegroups: "1", "2", and "3". From a high-
890 There are 3 versions of changegroups: "1", "2", and "3". From a high-
890 level, versions "1" and "2" are almost exactly the same, with the only
891 level, versions "1" and "2" are almost exactly the same, with the only
891 difference being a header on entries in the changeset segment. Version "3"
892 difference being a header on entries in the changeset segment. Version "3"
892 adds support for exchanging treemanifests and includes revlog flags in the
893 adds support for exchanging treemanifests and includes revlog flags in the
893 delta header.
894 delta header.
894
895
895 Changegroups consists of 3 logical segments:
896 Changegroups consists of 3 logical segments:
896
897
897 +---------------------------------+
898 +---------------------------------+
898 | | | |
899 | | | |
899 | changeset | manifest | filelogs |
900 | changeset | manifest | filelogs |
900 | | | |
901 | | | |
901 +---------------------------------+
902 +---------------------------------+
902
903
903 The principle building block of each segment is a *chunk*. A *chunk* is a
904 The principle building block of each segment is a *chunk*. A *chunk* is a
904 framed piece of data:
905 framed piece of data:
905
906
906 +---------------------------------------+
907 +---------------------------------------+
907 | | |
908 | | |
908 | length | data |
909 | length | data |
909 | (32 bits) | <length> bytes |
910 | (32 bits) | <length> bytes |
910 | | |
911 | | |
911 +---------------------------------------+
912 +---------------------------------------+
912
913
913 Each chunk starts with a 32-bit big-endian signed integer indicating the
914 Each chunk starts with a 32-bit big-endian signed integer indicating the
914 length of the raw data that follows.
915 length of the raw data that follows.
915
916
916 There is a special case chunk that has 0 length ("0x00000000"). We call
917 There is a special case chunk that has 0 length ("0x00000000"). We call
917 this an *empty chunk*.
918 this an *empty chunk*.
918
919
919 Delta Groups
920 Delta Groups
920 ------------
921 ------------
921
922
922 A *delta group* expresses the content of a revlog as a series of deltas,
923 A *delta group* expresses the content of a revlog as a series of deltas,
923 or patches against previous revisions.
924 or patches against previous revisions.
924
925
925 Delta groups consist of 0 or more *chunks* followed by the *empty chunk*
926 Delta groups consist of 0 or more *chunks* followed by the *empty chunk*
926 to signal the end of the delta group:
927 to signal the end of the delta group:
927
928
928 +------------------------------------------------------------------------+
929 +------------------------------------------------------------------------+
929 | | | | | |
930 | | | | | |
930 | chunk0 length | chunk0 data | chunk1 length | chunk1 data | 0x0 |
931 | chunk0 length | chunk0 data | chunk1 length | chunk1 data | 0x0 |
931 | (32 bits) | (various) | (32 bits) | (various) | (32 bits) |
932 | (32 bits) | (various) | (32 bits) | (various) | (32 bits) |
932 | | | | | |
933 | | | | | |
933 +------------------------------------------------------------+-----------+
934 +------------------------------------------------------------+-----------+
934
935
935 Each *chunk*'s data consists of the following:
936 Each *chunk*'s data consists of the following:
936
937
937 +-----------------------------------------+
938 +-----------------------------------------+
938 | | | |
939 | | | |
939 | delta header | mdiff header | delta |
940 | delta header | mdiff header | delta |
940 | (various) | (12 bytes) | (various) |
941 | (various) | (12 bytes) | (various) |
941 | | | |
942 | | | |
942 +-----------------------------------------+
943 +-----------------------------------------+
943
944
944 The *length* field is the byte length of the remaining 3 logical pieces of
945 The *length* field is the byte length of the remaining 3 logical pieces of
945 data. The *delta* is a diff from an existing entry in the changelog.
946 data. The *delta* is a diff from an existing entry in the changelog.
946
947
947 The *delta header* is different between versions "1", "2", and "3" of the
948 The *delta header* is different between versions "1", "2", and "3" of the
948 changegroup format.
949 changegroup format.
949
950
950 Version 1:
951 Version 1:
951
952
952 +------------------------------------------------------+
953 +------------------------------------------------------+
953 | | | | |
954 | | | | |
954 | node | p1 node | p2 node | link node |
955 | node | p1 node | p2 node | link node |
955 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
956 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
956 | | | | |
957 | | | | |
957 +------------------------------------------------------+
958 +------------------------------------------------------+
958
959
959 Version 2:
960 Version 2:
960
961
961 +------------------------------------------------------------------+
962 +------------------------------------------------------------------+
962 | | | | | |
963 | | | | | |
963 | node | p1 node | p2 node | base node | link node |
964 | node | p1 node | p2 node | base node | link node |
964 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
965 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
965 | | | | | |
966 | | | | | |
966 +------------------------------------------------------------------+
967 +------------------------------------------------------------------+
967
968
968 Version 3:
969 Version 3:
969
970
970 +------------------------------------------------------------------------------+
971 +------------------------------------------------------------------------------+
971 | | | | | | |
972 | | | | | | |
972 | node | p1 node | p2 node | base node | link node | flags |
973 | node | p1 node | p2 node | base node | link node | flags |
973 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (2 bytes) |
974 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (2 bytes) |
974 | | | | | | |
975 | | | | | | |
975 +------------------------------------------------------------------------------+
976 +------------------------------------------------------------------------------+
976
977
977 The *mdiff header* consists of 3 32-bit big-endian signed integers
978 The *mdiff header* consists of 3 32-bit big-endian signed integers
978 describing offsets at which to apply the following delta content:
979 describing offsets at which to apply the following delta content:
979
980
980 +-------------------------------------+
981 +-------------------------------------+
981 | | | |
982 | | | |
982 | offset | old length | new length |
983 | offset | old length | new length |
983 | (32 bits) | (32 bits) | (32 bits) |
984 | (32 bits) | (32 bits) | (32 bits) |
984 | | | |
985 | | | |
985 +-------------------------------------+
986 +-------------------------------------+
986
987
987 In version 1, the delta is always applied against the previous node from
988 In version 1, the delta is always applied against the previous node from
988 the changegroup or the first parent if this is the first entry in the
989 the changegroup or the first parent if this is the first entry in the
989 changegroup.
990 changegroup.
990
991
991 In version 2, the delta base node is encoded in the entry in the
992 In version 2, the delta base node is encoded in the entry in the
992 changegroup. This allows the delta to be expressed against any parent,
993 changegroup. This allows the delta to be expressed against any parent,
993 which can result in smaller deltas and more efficient encoding of data.
994 which can result in smaller deltas and more efficient encoding of data.
994
995
995 Changeset Segment
996 Changeset Segment
996 -----------------
997 -----------------
997
998
998 The *changeset segment* consists of a single *delta group* holding
999 The *changeset segment* consists of a single *delta group* holding
999 changelog data. It is followed by an *empty chunk* to denote the boundary
1000 changelog data. It is followed by an *empty chunk* to denote the boundary
1000 to the *manifests segment*.
1001 to the *manifests segment*.
1001
1002
1002 Manifest Segment
1003 Manifest Segment
1003 ----------------
1004 ----------------
1004
1005
1005 The *manifest segment* consists of a single *delta group* holding manifest
1006 The *manifest segment* consists of a single *delta group* holding manifest
1006 data. It is followed by an *empty chunk* to denote the boundary to the
1007 data. It is followed by an *empty chunk* to denote the boundary to the
1007 *filelogs segment*.
1008 *filelogs segment*.
1008
1009
1009 Filelogs Segment
1010 Filelogs Segment
1010 ----------------
1011 ----------------
1011
1012
1012 The *filelogs* segment consists of multiple sub-segments, each
1013 The *filelogs* segment consists of multiple sub-segments, each
1013 corresponding to an individual file whose data is being described:
1014 corresponding to an individual file whose data is being described:
1014
1015
1015 +--------------------------------------+
1016 +--------------------------------------+
1016 | | | | |
1017 | | | | |
1017 | filelog0 | filelog1 | filelog2 | ... |
1018 | filelog0 | filelog1 | filelog2 | ... |
1018 | | | | |
1019 | | | | |
1019 +--------------------------------------+
1020 +--------------------------------------+
1020
1021
1021 In version "3" of the changegroup format, filelogs may include directory
1022 In version "3" of the changegroup format, filelogs may include directory
1022 logs when treemanifests are in use. directory logs are identified by
1023 logs when treemanifests are in use. directory logs are identified by
1023 having a trailing '/' on their filename (see below).
1024 having a trailing '/' on their filename (see below).
1024
1025
1025 The final filelog sub-segment is followed by an *empty chunk* to denote
1026 The final filelog sub-segment is followed by an *empty chunk* to denote
1026 the end of the segment and the overall changegroup.
1027 the end of the segment and the overall changegroup.
1027
1028
1028 Each filelog sub-segment consists of the following:
1029 Each filelog sub-segment consists of the following:
1029
1030
1030 +------------------------------------------+
1031 +------------------------------------------+
1031 | | | |
1032 | | | |
1032 | filename size | filename | delta group |
1033 | filename size | filename | delta group |
1033 | (32 bits) | (various) | (various) |
1034 | (32 bits) | (various) | (various) |
1034 | | | |
1035 | | | |
1035 +------------------------------------------+
1036 +------------------------------------------+
1036
1037
1037 That is, a *chunk* consisting of the filename (not terminated or padded)
1038 That is, a *chunk* consisting of the filename (not terminated or padded)
1038 followed by N chunks constituting the *delta group* for this file.
1039 followed by N chunks constituting the *delta group* for this file.
1039
1040
1040 Test list of commands with command with no help text
1041 Test list of commands with command with no help text
1041
1042
1042 $ hg help helpext
1043 $ hg help helpext
1043 helpext extension - no help text available
1044 helpext extension - no help text available
1044
1045
1045 list of commands:
1046 list of commands:
1046
1047
1047 nohelp (no help text available)
1048 nohelp (no help text available)
1048
1049
1049 (use "hg help -v helpext" to show built-in aliases and global options)
1050 (use "hg help -v helpext" to show built-in aliases and global options)
1050
1051
1051
1052
1052 test deprecated and experimental options are hidden in command help
1053 test deprecated and experimental options are hidden in command help
1053 $ hg help debugoptDEP
1054 $ hg help debugoptDEP
1054 hg debugoptDEP
1055 hg debugoptDEP
1055
1056
1056 (no help text available)
1057 (no help text available)
1057
1058
1058 options:
1059 options:
1059
1060
1060 (some details hidden, use --verbose to show complete help)
1061 (some details hidden, use --verbose to show complete help)
1061
1062
1062 $ hg help debugoptEXP
1063 $ hg help debugoptEXP
1063 hg debugoptEXP
1064 hg debugoptEXP
1064
1065
1065 (no help text available)
1066 (no help text available)
1066
1067
1067 options:
1068 options:
1068
1069
1069 (some details hidden, use --verbose to show complete help)
1070 (some details hidden, use --verbose to show complete help)
1070
1071
1071 test deprecated and experimental options is shown with -v
1072 test deprecated and experimental options is shown with -v
1072 $ hg help -v debugoptDEP | grep dopt
1073 $ hg help -v debugoptDEP | grep dopt
1073 --dopt option is (DEPRECATED)
1074 --dopt option is (DEPRECATED)
1074 $ hg help -v debugoptEXP | grep eopt
1075 $ hg help -v debugoptEXP | grep eopt
1075 --eopt option is (EXPERIMENTAL)
1076 --eopt option is (EXPERIMENTAL)
1076
1077
1077 #if gettext
1078 #if gettext
1078 test deprecated option is hidden with translation with untranslated description
1079 test deprecated option is hidden with translation with untranslated description
1079 (use many globy for not failing on changed transaction)
1080 (use many globy for not failing on changed transaction)
1080 $ LANGUAGE=sv hg help debugoptDEP
1081 $ LANGUAGE=sv hg help debugoptDEP
1081 hg debugoptDEP
1082 hg debugoptDEP
1082
1083
1083 (*) (glob)
1084 (*) (glob)
1084
1085
1085 options:
1086 options:
1086
1087
1087 (some details hidden, use --verbose to show complete help)
1088 (some details hidden, use --verbose to show complete help)
1088 #endif
1089 #endif
1089
1090
1090 Test commands that collide with topics (issue4240)
1091 Test commands that collide with topics (issue4240)
1091
1092
1092 $ hg config -hq
1093 $ hg config -hq
1093 hg config [-u] [NAME]...
1094 hg config [-u] [NAME]...
1094
1095
1095 show combined config settings from all hgrc files
1096 show combined config settings from all hgrc files
1096 $ hg showconfig -hq
1097 $ hg showconfig -hq
1097 hg config [-u] [NAME]...
1098 hg config [-u] [NAME]...
1098
1099
1099 show combined config settings from all hgrc files
1100 show combined config settings from all hgrc files
1100
1101
1101 Test a help topic
1102 Test a help topic
1102
1103
1103 $ hg help revs
1104 $ hg help revs
1104 Specifying Single Revisions
1105 Specifying Single Revisions
1105 """""""""""""""""""""""""""
1106 """""""""""""""""""""""""""
1106
1107
1107 Mercurial supports several ways to specify individual revisions.
1108 Mercurial supports several ways to specify individual revisions.
1108
1109
1109 A plain integer is treated as a revision number. Negative integers are
1110 A plain integer is treated as a revision number. Negative integers are
1110 treated as sequential offsets from the tip, with -1 denoting the tip, -2
1111 treated as sequential offsets from the tip, with -1 denoting the tip, -2
1111 denoting the revision prior to the tip, and so forth.
1112 denoting the revision prior to the tip, and so forth.
1112
1113
1113 A 40-digit hexadecimal string is treated as a unique revision identifier.
1114 A 40-digit hexadecimal string is treated as a unique revision identifier.
1114
1115
1115 A hexadecimal string less than 40 characters long is treated as a unique
1116 A hexadecimal string less than 40 characters long is treated as a unique
1116 revision identifier and is referred to as a short-form identifier. A
1117 revision identifier and is referred to as a short-form identifier. A
1117 short-form identifier is only valid if it is the prefix of exactly one
1118 short-form identifier is only valid if it is the prefix of exactly one
1118 full-length identifier.
1119 full-length identifier.
1119
1120
1120 Any other string is treated as a bookmark, tag, or branch name. A bookmark
1121 Any other string is treated as a bookmark, tag, or branch name. A bookmark
1121 is a movable pointer to a revision. A tag is a permanent name associated
1122 is a movable pointer to a revision. A tag is a permanent name associated
1122 with a revision. A branch name denotes the tipmost open branch head of
1123 with a revision. A branch name denotes the tipmost open branch head of
1123 that branch - or if they are all closed, the tipmost closed head of the
1124 that branch - or if they are all closed, the tipmost closed head of the
1124 branch. Bookmark, tag, and branch names must not contain the ":"
1125 branch. Bookmark, tag, and branch names must not contain the ":"
1125 character.
1126 character.
1126
1127
1127 The reserved name "tip" always identifies the most recent revision.
1128 The reserved name "tip" always identifies the most recent revision.
1128
1129
1129 The reserved name "null" indicates the null revision. This is the revision
1130 The reserved name "null" indicates the null revision. This is the revision
1130 of an empty repository, and the parent of revision 0.
1131 of an empty repository, and the parent of revision 0.
1131
1132
1132 The reserved name "." indicates the working directory parent. If no
1133 The reserved name "." indicates the working directory parent. If no
1133 working directory is checked out, it is equivalent to null. If an
1134 working directory is checked out, it is equivalent to null. If an
1134 uncommitted merge is in progress, "." is the revision of the first parent.
1135 uncommitted merge is in progress, "." is the revision of the first parent.
1135
1136
1136 Test repeated config section name
1137 Test repeated config section name
1137
1138
1138 $ hg help config.host
1139 $ hg help config.host
1139 "http_proxy.host"
1140 "http_proxy.host"
1140 Host name and (optional) port of the proxy server, for example
1141 Host name and (optional) port of the proxy server, for example
1141 "myproxy:8000".
1142 "myproxy:8000".
1142
1143
1143 "smtp.host"
1144 "smtp.host"
1144 Host name of mail server, e.g. "mail.example.com".
1145 Host name of mail server, e.g. "mail.example.com".
1145
1146
1146 Unrelated trailing paragraphs shouldn't be included
1147 Unrelated trailing paragraphs shouldn't be included
1147
1148
1148 $ hg help config.extramsg | grep '^$'
1149 $ hg help config.extramsg | grep '^$'
1149
1150
1150
1151
1151 Test capitalized section name
1152 Test capitalized section name
1152
1153
1153 $ hg help scripting.HGPLAIN > /dev/null
1154 $ hg help scripting.HGPLAIN > /dev/null
1154
1155
1155 Help subsection:
1156 Help subsection:
1156
1157
1157 $ hg help config.charsets |grep "Email example:" > /dev/null
1158 $ hg help config.charsets |grep "Email example:" > /dev/null
1158 [1]
1159 [1]
1159
1160
1160 Show nested definitions
1161 Show nested definitions
1161 ("profiling.type"[break]"ls"[break]"stat"[break])
1162 ("profiling.type"[break]"ls"[break]"stat"[break])
1162
1163
1163 $ hg help config.type | egrep '^$'|wc -l
1164 $ hg help config.type | egrep '^$'|wc -l
1164 \s*3 (re)
1165 \s*3 (re)
1165
1166
1166 Separate sections from subsections
1167 Separate sections from subsections
1167
1168
1168 $ hg help config.format | egrep '^ ("|-)|^\s*$' | uniq
1169 $ hg help config.format | egrep '^ ("|-)|^\s*$' | uniq
1169 "format"
1170 "format"
1170 --------
1171 --------
1171
1172
1172 "usegeneraldelta"
1173 "usegeneraldelta"
1173
1174
1174 "dotencode"
1175 "dotencode"
1175
1176
1176 "usefncache"
1177 "usefncache"
1177
1178
1178 "usestore"
1179 "usestore"
1179
1180
1180 "profiling"
1181 "profiling"
1181 -----------
1182 -----------
1182
1183
1183 "format"
1184 "format"
1184
1185
1185 "progress"
1186 "progress"
1186 ----------
1187 ----------
1187
1188
1188 "format"
1189 "format"
1189
1190
1190
1191
1191 Last item in help config.*:
1192 Last item in help config.*:
1192
1193
1193 $ hg help config.`hg help config|grep '^ "'| \
1194 $ hg help config.`hg help config|grep '^ "'| \
1194 > tail -1|sed 's![ "]*!!g'`| \
1195 > tail -1|sed 's![ "]*!!g'`| \
1195 > grep "hg help -c config" > /dev/null
1196 > grep "hg help -c config" > /dev/null
1196 [1]
1197 [1]
1197
1198
1198 note to use help -c for general hg help config:
1199 note to use help -c for general hg help config:
1199
1200
1200 $ hg help config |grep "hg help -c config" > /dev/null
1201 $ hg help config |grep "hg help -c config" > /dev/null
1201
1202
1202 Test templating help
1203 Test templating help
1203
1204
1204 $ hg help templating | egrep '(desc|diffstat|firstline|nonempty) '
1205 $ hg help templating | egrep '(desc|diffstat|firstline|nonempty) '
1205 desc String. The text of the changeset description.
1206 desc String. The text of the changeset description.
1206 diffstat String. Statistics of changes with the following format:
1207 diffstat String. Statistics of changes with the following format:
1207 firstline Any text. Returns the first line of text.
1208 firstline Any text. Returns the first line of text.
1208 nonempty Any text. Returns '(none)' if the string is empty.
1209 nonempty Any text. Returns '(none)' if the string is empty.
1209
1210
1210 Test deprecated items
1211 Test deprecated items
1211
1212
1212 $ hg help -v templating | grep currentbookmark
1213 $ hg help -v templating | grep currentbookmark
1213 currentbookmark
1214 currentbookmark
1214 $ hg help templating | (grep currentbookmark || true)
1215 $ hg help templating | (grep currentbookmark || true)
1215
1216
1216 Test help hooks
1217 Test help hooks
1217
1218
1218 $ cat > helphook1.py <<EOF
1219 $ cat > helphook1.py <<EOF
1219 > from mercurial import help
1220 > from mercurial import help
1220 >
1221 >
1221 > def rewrite(ui, topic, doc):
1222 > def rewrite(ui, topic, doc):
1222 > return doc + '\nhelphook1\n'
1223 > return doc + '\nhelphook1\n'
1223 >
1224 >
1224 > def extsetup(ui):
1225 > def extsetup(ui):
1225 > help.addtopichook('revsets', rewrite)
1226 > help.addtopichook('revsets', rewrite)
1226 > EOF
1227 > EOF
1227 $ cat > helphook2.py <<EOF
1228 $ cat > helphook2.py <<EOF
1228 > from mercurial import help
1229 > from mercurial import help
1229 >
1230 >
1230 > def rewrite(ui, topic, doc):
1231 > def rewrite(ui, topic, doc):
1231 > return doc + '\nhelphook2\n'
1232 > return doc + '\nhelphook2\n'
1232 >
1233 >
1233 > def extsetup(ui):
1234 > def extsetup(ui):
1234 > help.addtopichook('revsets', rewrite)
1235 > help.addtopichook('revsets', rewrite)
1235 > EOF
1236 > EOF
1236 $ echo '[extensions]' >> $HGRCPATH
1237 $ echo '[extensions]' >> $HGRCPATH
1237 $ echo "helphook1 = `pwd`/helphook1.py" >> $HGRCPATH
1238 $ echo "helphook1 = `pwd`/helphook1.py" >> $HGRCPATH
1238 $ echo "helphook2 = `pwd`/helphook2.py" >> $HGRCPATH
1239 $ echo "helphook2 = `pwd`/helphook2.py" >> $HGRCPATH
1239 $ hg help revsets | grep helphook
1240 $ hg help revsets | grep helphook
1240 helphook1
1241 helphook1
1241 helphook2
1242 helphook2
1242
1243
1243 help -c should only show debug --debug
1244 help -c should only show debug --debug
1244
1245
1245 $ hg help -c --debug|egrep debug|wc -l|egrep '^\s*0\s*$'
1246 $ hg help -c --debug|egrep debug|wc -l|egrep '^\s*0\s*$'
1246 [1]
1247 [1]
1247
1248
1248 help -c should only show deprecated for -v
1249 help -c should only show deprecated for -v
1249
1250
1250 $ hg help -c -v|egrep DEPRECATED|wc -l|egrep '^\s*0\s*$'
1251 $ hg help -c -v|egrep DEPRECATED|wc -l|egrep '^\s*0\s*$'
1251 [1]
1252 [1]
1252
1253
1253 Test -e / -c / -k combinations
1254 Test -e / -c / -k combinations
1254
1255
1255 $ hg help -c|egrep '^[A-Z].*:|^ debug'
1256 $ hg help -c|egrep '^[A-Z].*:|^ debug'
1256 Commands:
1257 Commands:
1257 $ hg help -e|egrep '^[A-Z].*:|^ debug'
1258 $ hg help -e|egrep '^[A-Z].*:|^ debug'
1258 Extensions:
1259 Extensions:
1259 $ hg help -k|egrep '^[A-Z].*:|^ debug'
1260 $ hg help -k|egrep '^[A-Z].*:|^ debug'
1260 Topics:
1261 Topics:
1261 Commands:
1262 Commands:
1262 Extensions:
1263 Extensions:
1263 Extension Commands:
1264 Extension Commands:
1264 $ hg help -c schemes
1265 $ hg help -c schemes
1265 abort: no such help topic: schemes
1266 abort: no such help topic: schemes
1266 (try "hg help --keyword schemes")
1267 (try "hg help --keyword schemes")
1267 [255]
1268 [255]
1268 $ hg help -e schemes |head -1
1269 $ hg help -e schemes |head -1
1269 schemes extension - extend schemes with shortcuts to repository swarms
1270 schemes extension - extend schemes with shortcuts to repository swarms
1270 $ hg help -c -k dates |egrep '^(Topics|Extensions|Commands):'
1271 $ hg help -c -k dates |egrep '^(Topics|Extensions|Commands):'
1271 Commands:
1272 Commands:
1272 $ hg help -e -k a |egrep '^(Topics|Extensions|Commands):'
1273 $ hg help -e -k a |egrep '^(Topics|Extensions|Commands):'
1273 Extensions:
1274 Extensions:
1274 $ hg help -e -c -k date |egrep '^(Topics|Extensions|Commands):'
1275 $ hg help -e -c -k date |egrep '^(Topics|Extensions|Commands):'
1275 Extensions:
1276 Extensions:
1276 Commands:
1277 Commands:
1277 $ hg help -c commit > /dev/null
1278 $ hg help -c commit > /dev/null
1278 $ hg help -e -c commit > /dev/null
1279 $ hg help -e -c commit > /dev/null
1279 $ hg help -e commit > /dev/null
1280 $ hg help -e commit > /dev/null
1280 abort: no such help topic: commit
1281 abort: no such help topic: commit
1281 (try "hg help --keyword commit")
1282 (try "hg help --keyword commit")
1282 [255]
1283 [255]
1283
1284
1284 Test keyword search help
1285 Test keyword search help
1285
1286
1286 $ cat > prefixedname.py <<EOF
1287 $ cat > prefixedname.py <<EOF
1287 > '''matched against word "clone"
1288 > '''matched against word "clone"
1288 > '''
1289 > '''
1289 > EOF
1290 > EOF
1290 $ echo '[extensions]' >> $HGRCPATH
1291 $ echo '[extensions]' >> $HGRCPATH
1291 $ echo "dot.dot.prefixedname = `pwd`/prefixedname.py" >> $HGRCPATH
1292 $ echo "dot.dot.prefixedname = `pwd`/prefixedname.py" >> $HGRCPATH
1292 $ hg help -k clone
1293 $ hg help -k clone
1293 Topics:
1294 Topics:
1294
1295
1295 config Configuration Files
1296 config Configuration Files
1296 extensions Using Additional Features
1297 extensions Using Additional Features
1297 glossary Glossary
1298 glossary Glossary
1298 phases Working with Phases
1299 phases Working with Phases
1299 subrepos Subrepositories
1300 subrepos Subrepositories
1300 urls URL Paths
1301 urls URL Paths
1301
1302
1302 Commands:
1303 Commands:
1303
1304
1304 bookmarks create a new bookmark or list existing bookmarks
1305 bookmarks create a new bookmark or list existing bookmarks
1305 clone make a copy of an existing repository
1306 clone make a copy of an existing repository
1306 paths show aliases for remote repositories
1307 paths show aliases for remote repositories
1307 update update working directory (or switch revisions)
1308 update update working directory (or switch revisions)
1308
1309
1309 Extensions:
1310 Extensions:
1310
1311
1311 clonebundles advertise pre-generated bundles to seed clones (experimental)
1312 clonebundles advertise pre-generated bundles to seed clones (experimental)
1312 prefixedname matched against word "clone"
1313 prefixedname matched against word "clone"
1313 relink recreates hardlinks between repository clones
1314 relink recreates hardlinks between repository clones
1314
1315
1315 Extension Commands:
1316 Extension Commands:
1316
1317
1317 qclone clone main and patch repository at same time
1318 qclone clone main and patch repository at same time
1318
1319
1319 Test unfound topic
1320 Test unfound topic
1320
1321
1321 $ hg help nonexistingtopicthatwillneverexisteverever
1322 $ hg help nonexistingtopicthatwillneverexisteverever
1322 abort: no such help topic: nonexistingtopicthatwillneverexisteverever
1323 abort: no such help topic: nonexistingtopicthatwillneverexisteverever
1323 (try "hg help --keyword nonexistingtopicthatwillneverexisteverever")
1324 (try "hg help --keyword nonexistingtopicthatwillneverexisteverever")
1324 [255]
1325 [255]
1325
1326
1326 Test unfound keyword
1327 Test unfound keyword
1327
1328
1328 $ hg help --keyword nonexistingwordthatwillneverexisteverever
1329 $ hg help --keyword nonexistingwordthatwillneverexisteverever
1329 abort: no matches
1330 abort: no matches
1330 (try "hg help" for a list of topics)
1331 (try "hg help" for a list of topics)
1331 [255]
1332 [255]
1332
1333
1333 Test omit indicating for help
1334 Test omit indicating for help
1334
1335
1335 $ cat > addverboseitems.py <<EOF
1336 $ cat > addverboseitems.py <<EOF
1336 > '''extension to test omit indicating.
1337 > '''extension to test omit indicating.
1337 >
1338 >
1338 > This paragraph is never omitted (for extension)
1339 > This paragraph is never omitted (for extension)
1339 >
1340 >
1340 > .. container:: verbose
1341 > .. container:: verbose
1341 >
1342 >
1342 > This paragraph is omitted,
1343 > This paragraph is omitted,
1343 > if :hg:\`help\` is invoked without \`\`-v\`\` (for extension)
1344 > if :hg:\`help\` is invoked without \`\`-v\`\` (for extension)
1344 >
1345 >
1345 > This paragraph is never omitted, too (for extension)
1346 > This paragraph is never omitted, too (for extension)
1346 > '''
1347 > '''
1347 >
1348 >
1348 > from mercurial import help, commands
1349 > from mercurial import help, commands
1349 > testtopic = """This paragraph is never omitted (for topic).
1350 > testtopic = """This paragraph is never omitted (for topic).
1350 >
1351 >
1351 > .. container:: verbose
1352 > .. container:: verbose
1352 >
1353 >
1353 > This paragraph is omitted,
1354 > This paragraph is omitted,
1354 > if :hg:\`help\` is invoked without \`\`-v\`\` (for topic)
1355 > if :hg:\`help\` is invoked without \`\`-v\`\` (for topic)
1355 >
1356 >
1356 > This paragraph is never omitted, too (for topic)
1357 > This paragraph is never omitted, too (for topic)
1357 > """
1358 > """
1358 > def extsetup(ui):
1359 > def extsetup(ui):
1359 > help.helptable.append((["topic-containing-verbose"],
1360 > help.helptable.append((["topic-containing-verbose"],
1360 > "This is the topic to test omit indicating.",
1361 > "This is the topic to test omit indicating.",
1361 > lambda ui: testtopic))
1362 > lambda ui: testtopic))
1362 > EOF
1363 > EOF
1363 $ echo '[extensions]' >> $HGRCPATH
1364 $ echo '[extensions]' >> $HGRCPATH
1364 $ echo "addverboseitems = `pwd`/addverboseitems.py" >> $HGRCPATH
1365 $ echo "addverboseitems = `pwd`/addverboseitems.py" >> $HGRCPATH
1365 $ hg help addverboseitems
1366 $ hg help addverboseitems
1366 addverboseitems extension - extension to test omit indicating.
1367 addverboseitems extension - extension to test omit indicating.
1367
1368
1368 This paragraph is never omitted (for extension)
1369 This paragraph is never omitted (for extension)
1369
1370
1370 This paragraph is never omitted, too (for extension)
1371 This paragraph is never omitted, too (for extension)
1371
1372
1372 (some details hidden, use --verbose to show complete help)
1373 (some details hidden, use --verbose to show complete help)
1373
1374
1374 no commands defined
1375 no commands defined
1375 $ hg help -v addverboseitems
1376 $ hg help -v addverboseitems
1376 addverboseitems extension - extension to test omit indicating.
1377 addverboseitems extension - extension to test omit indicating.
1377
1378
1378 This paragraph is never omitted (for extension)
1379 This paragraph is never omitted (for extension)
1379
1380
1380 This paragraph is omitted, if "hg help" is invoked without "-v" (for
1381 This paragraph is omitted, if "hg help" is invoked without "-v" (for
1381 extension)
1382 extension)
1382
1383
1383 This paragraph is never omitted, too (for extension)
1384 This paragraph is never omitted, too (for extension)
1384
1385
1385 no commands defined
1386 no commands defined
1386 $ hg help topic-containing-verbose
1387 $ hg help topic-containing-verbose
1387 This is the topic to test omit indicating.
1388 This is the topic to test omit indicating.
1388 """"""""""""""""""""""""""""""""""""""""""
1389 """"""""""""""""""""""""""""""""""""""""""
1389
1390
1390 This paragraph is never omitted (for topic).
1391 This paragraph is never omitted (for topic).
1391
1392
1392 This paragraph is never omitted, too (for topic)
1393 This paragraph is never omitted, too (for topic)
1393
1394
1394 (some details hidden, use --verbose to show complete help)
1395 (some details hidden, use --verbose to show complete help)
1395 $ hg help -v topic-containing-verbose
1396 $ hg help -v topic-containing-verbose
1396 This is the topic to test omit indicating.
1397 This is the topic to test omit indicating.
1397 """"""""""""""""""""""""""""""""""""""""""
1398 """"""""""""""""""""""""""""""""""""""""""
1398
1399
1399 This paragraph is never omitted (for topic).
1400 This paragraph is never omitted (for topic).
1400
1401
1401 This paragraph is omitted, if "hg help" is invoked without "-v" (for
1402 This paragraph is omitted, if "hg help" is invoked without "-v" (for
1402 topic)
1403 topic)
1403
1404
1404 This paragraph is never omitted, too (for topic)
1405 This paragraph is never omitted, too (for topic)
1405
1406
1406 Test section lookup
1407 Test section lookup
1407
1408
1408 $ hg help revset.merge
1409 $ hg help revset.merge
1409 "merge()"
1410 "merge()"
1410 Changeset is a merge changeset.
1411 Changeset is a merge changeset.
1411
1412
1412 $ hg help glossary.dag
1413 $ hg help glossary.dag
1413 DAG
1414 DAG
1414 The repository of changesets of a distributed version control system
1415 The repository of changesets of a distributed version control system
1415 (DVCS) can be described as a directed acyclic graph (DAG), consisting
1416 (DVCS) can be described as a directed acyclic graph (DAG), consisting
1416 of nodes and edges, where nodes correspond to changesets and edges
1417 of nodes and edges, where nodes correspond to changesets and edges
1417 imply a parent -> child relation. This graph can be visualized by
1418 imply a parent -> child relation. This graph can be visualized by
1418 graphical tools such as "hg log --graph". In Mercurial, the DAG is
1419 graphical tools such as "hg log --graph". In Mercurial, the DAG is
1419 limited by the requirement for children to have at most two parents.
1420 limited by the requirement for children to have at most two parents.
1420
1421
1421
1422
1422 $ hg help hgrc.paths
1423 $ hg help hgrc.paths
1423 "paths"
1424 "paths"
1424 -------
1425 -------
1425
1426
1426 Assigns symbolic names and behavior to repositories.
1427 Assigns symbolic names and behavior to repositories.
1427
1428
1428 Options are symbolic names defining the URL or directory that is the
1429 Options are symbolic names defining the URL or directory that is the
1429 location of the repository. Example:
1430 location of the repository. Example:
1430
1431
1431 [paths]
1432 [paths]
1432 my_server = https://example.com/my_repo
1433 my_server = https://example.com/my_repo
1433 local_path = /home/me/repo
1434 local_path = /home/me/repo
1434
1435
1435 These symbolic names can be used from the command line. To pull from
1436 These symbolic names can be used from the command line. To pull from
1436 "my_server": "hg pull my_server". To push to "local_path": "hg push
1437 "my_server": "hg pull my_server". To push to "local_path": "hg push
1437 local_path".
1438 local_path".
1438
1439
1439 Options containing colons (":") denote sub-options that can influence
1440 Options containing colons (":") denote sub-options that can influence
1440 behavior for that specific path. Example:
1441 behavior for that specific path. Example:
1441
1442
1442 [paths]
1443 [paths]
1443 my_server = https://example.com/my_path
1444 my_server = https://example.com/my_path
1444 my_server:pushurl = ssh://example.com/my_path
1445 my_server:pushurl = ssh://example.com/my_path
1445
1446
1446 The following sub-options can be defined:
1447 The following sub-options can be defined:
1447
1448
1448 "pushurl"
1449 "pushurl"
1449 The URL to use for push operations. If not defined, the location
1450 The URL to use for push operations. If not defined, the location
1450 defined by the path's main entry is used.
1451 defined by the path's main entry is used.
1451
1452
1452 The following special named paths exist:
1453 The following special named paths exist:
1453
1454
1454 "default"
1455 "default"
1455 The URL or directory to use when no source or remote is specified.
1456 The URL or directory to use when no source or remote is specified.
1456
1457
1457 "hg clone" will automatically define this path to the location the
1458 "hg clone" will automatically define this path to the location the
1458 repository was cloned from.
1459 repository was cloned from.
1459
1460
1460 "default-push"
1461 "default-push"
1461 (deprecated) The URL or directory for the default "hg push" location.
1462 (deprecated) The URL or directory for the default "hg push" location.
1462 "default:pushurl" should be used instead.
1463 "default:pushurl" should be used instead.
1463
1464
1464 $ hg help glossary.mcguffin
1465 $ hg help glossary.mcguffin
1465 abort: help section not found
1466 abort: help section not found
1466 [255]
1467 [255]
1467
1468
1468 $ hg help glossary.mc.guffin
1469 $ hg help glossary.mc.guffin
1469 abort: help section not found
1470 abort: help section not found
1470 [255]
1471 [255]
1471
1472
1472 $ hg help template.files
1473 $ hg help template.files
1473 files List of strings. All files modified, added, or removed by
1474 files List of strings. All files modified, added, or removed by
1474 this changeset.
1475 this changeset.
1475
1476
1476 Test dynamic list of merge tools only shows up once
1477 Test dynamic list of merge tools only shows up once
1477 $ hg help merge-tools
1478 $ hg help merge-tools
1478 Merge Tools
1479 Merge Tools
1479 """""""""""
1480 """""""""""
1480
1481
1481 To merge files Mercurial uses merge tools.
1482 To merge files Mercurial uses merge tools.
1482
1483
1483 A merge tool combines two different versions of a file into a merged file.
1484 A merge tool combines two different versions of a file into a merged file.
1484 Merge tools are given the two files and the greatest common ancestor of
1485 Merge tools are given the two files and the greatest common ancestor of
1485 the two file versions, so they can determine the changes made on both
1486 the two file versions, so they can determine the changes made on both
1486 branches.
1487 branches.
1487
1488
1488 Merge tools are used both for "hg resolve", "hg merge", "hg update", "hg
1489 Merge tools are used both for "hg resolve", "hg merge", "hg update", "hg
1489 backout" and in several extensions.
1490 backout" and in several extensions.
1490
1491
1491 Usually, the merge tool tries to automatically reconcile the files by
1492 Usually, the merge tool tries to automatically reconcile the files by
1492 combining all non-overlapping changes that occurred separately in the two
1493 combining all non-overlapping changes that occurred separately in the two
1493 different evolutions of the same initial base file. Furthermore, some
1494 different evolutions of the same initial base file. Furthermore, some
1494 interactive merge programs make it easier to manually resolve conflicting
1495 interactive merge programs make it easier to manually resolve conflicting
1495 merges, either in a graphical way, or by inserting some conflict markers.
1496 merges, either in a graphical way, or by inserting some conflict markers.
1496 Mercurial does not include any interactive merge programs but relies on
1497 Mercurial does not include any interactive merge programs but relies on
1497 external tools for that.
1498 external tools for that.
1498
1499
1499 Available merge tools
1500 Available merge tools
1500 =====================
1501 =====================
1501
1502
1502 External merge tools and their properties are configured in the merge-
1503 External merge tools and their properties are configured in the merge-
1503 tools configuration section - see hgrc(5) - but they can often just be
1504 tools configuration section - see hgrc(5) - but they can often just be
1504 named by their executable.
1505 named by their executable.
1505
1506
1506 A merge tool is generally usable if its executable can be found on the
1507 A merge tool is generally usable if its executable can be found on the
1507 system and if it can handle the merge. The executable is found if it is an
1508 system and if it can handle the merge. The executable is found if it is an
1508 absolute or relative executable path or the name of an application in the
1509 absolute or relative executable path or the name of an application in the
1509 executable search path. The tool is assumed to be able to handle the merge
1510 executable search path. The tool is assumed to be able to handle the merge
1510 if it can handle symlinks if the file is a symlink, if it can handle
1511 if it can handle symlinks if the file is a symlink, if it can handle
1511 binary files if the file is binary, and if a GUI is available if the tool
1512 binary files if the file is binary, and if a GUI is available if the tool
1512 requires a GUI.
1513 requires a GUI.
1513
1514
1514 There are some internal merge tools which can be used. The internal merge
1515 There are some internal merge tools which can be used. The internal merge
1515 tools are:
1516 tools are:
1516
1517
1517 ":dump"
1518 ":dump"
1518 Creates three versions of the files to merge, containing the contents of
1519 Creates three versions of the files to merge, containing the contents of
1519 local, other and base. These files can then be used to perform a merge
1520 local, other and base. These files can then be used to perform a merge
1520 manually. If the file to be merged is named "a.txt", these files will
1521 manually. If the file to be merged is named "a.txt", these files will
1521 accordingly be named "a.txt.local", "a.txt.other" and "a.txt.base" and
1522 accordingly be named "a.txt.local", "a.txt.other" and "a.txt.base" and
1522 they will be placed in the same directory as "a.txt".
1523 they will be placed in the same directory as "a.txt".
1523
1524
1524 ":fail"
1525 ":fail"
1525 Rather than attempting to merge files that were modified on both
1526 Rather than attempting to merge files that were modified on both
1526 branches, it marks them as unresolved. The resolve command must be used
1527 branches, it marks them as unresolved. The resolve command must be used
1527 to resolve these conflicts.
1528 to resolve these conflicts.
1528
1529
1529 ":local"
1530 ":local"
1530 Uses the local version of files as the merged version.
1531 Uses the local version of files as the merged version.
1531
1532
1532 ":merge"
1533 ":merge"
1533 Uses the internal non-interactive simple merge algorithm for merging
1534 Uses the internal non-interactive simple merge algorithm for merging
1534 files. It will fail if there are any conflicts and leave markers in the
1535 files. It will fail if there are any conflicts and leave markers in the
1535 partially merged file. Markers will have two sections, one for each side
1536 partially merged file. Markers will have two sections, one for each side
1536 of merge.
1537 of merge.
1537
1538
1538 ":merge-local"
1539 ":merge-local"
1539 Like :merge, but resolve all conflicts non-interactively in favor of the
1540 Like :merge, but resolve all conflicts non-interactively in favor of the
1540 local changes.
1541 local changes.
1541
1542
1542 ":merge-other"
1543 ":merge-other"
1543 Like :merge, but resolve all conflicts non-interactively in favor of the
1544 Like :merge, but resolve all conflicts non-interactively in favor of the
1544 other changes.
1545 other changes.
1545
1546
1546 ":merge3"
1547 ":merge3"
1547 Uses the internal non-interactive simple merge algorithm for merging
1548 Uses the internal non-interactive simple merge algorithm for merging
1548 files. It will fail if there are any conflicts and leave markers in the
1549 files. It will fail if there are any conflicts and leave markers in the
1549 partially merged file. Marker will have three sections, one from each
1550 partially merged file. Marker will have three sections, one from each
1550 side of the merge and one for the base content.
1551 side of the merge and one for the base content.
1551
1552
1552 ":other"
1553 ":other"
1553 Uses the other version of files as the merged version.
1554 Uses the other version of files as the merged version.
1554
1555
1555 ":prompt"
1556 ":prompt"
1556 Asks the user which of the local or the other version to keep as the
1557 Asks the user which of the local or the other version to keep as the
1557 merged version.
1558 merged version.
1558
1559
1559 ":tagmerge"
1560 ":tagmerge"
1560 Uses the internal tag merge algorithm (experimental).
1561 Uses the internal tag merge algorithm (experimental).
1561
1562
1562 ":union"
1563 ":union"
1563 Uses the internal non-interactive simple merge algorithm for merging
1564 Uses the internal non-interactive simple merge algorithm for merging
1564 files. It will use both left and right sides for conflict regions. No
1565 files. It will use both left and right sides for conflict regions. No
1565 markers are inserted.
1566 markers are inserted.
1566
1567
1567 Internal tools are always available and do not require a GUI but will by
1568 Internal tools are always available and do not require a GUI but will by
1568 default not handle symlinks or binary files.
1569 default not handle symlinks or binary files.
1569
1570
1570 Choosing a merge tool
1571 Choosing a merge tool
1571 =====================
1572 =====================
1572
1573
1573 Mercurial uses these rules when deciding which merge tool to use:
1574 Mercurial uses these rules when deciding which merge tool to use:
1574
1575
1575 1. If a tool has been specified with the --tool option to merge or
1576 1. If a tool has been specified with the --tool option to merge or
1576 resolve, it is used. If it is the name of a tool in the merge-tools
1577 resolve, it is used. If it is the name of a tool in the merge-tools
1577 configuration, its configuration is used. Otherwise the specified tool
1578 configuration, its configuration is used. Otherwise the specified tool
1578 must be executable by the shell.
1579 must be executable by the shell.
1579 2. If the "HGMERGE" environment variable is present, its value is used and
1580 2. If the "HGMERGE" environment variable is present, its value is used and
1580 must be executable by the shell.
1581 must be executable by the shell.
1581 3. If the filename of the file to be merged matches any of the patterns in
1582 3. If the filename of the file to be merged matches any of the patterns in
1582 the merge-patterns configuration section, the first usable merge tool
1583 the merge-patterns configuration section, the first usable merge tool
1583 corresponding to a matching pattern is used. Here, binary capabilities
1584 corresponding to a matching pattern is used. Here, binary capabilities
1584 of the merge tool are not considered.
1585 of the merge tool are not considered.
1585 4. If ui.merge is set it will be considered next. If the value is not the
1586 4. If ui.merge is set it will be considered next. If the value is not the
1586 name of a configured tool, the specified value is used and must be
1587 name of a configured tool, the specified value is used and must be
1587 executable by the shell. Otherwise the named tool is used if it is
1588 executable by the shell. Otherwise the named tool is used if it is
1588 usable.
1589 usable.
1589 5. If any usable merge tools are present in the merge-tools configuration
1590 5. If any usable merge tools are present in the merge-tools configuration
1590 section, the one with the highest priority is used.
1591 section, the one with the highest priority is used.
1591 6. If a program named "hgmerge" can be found on the system, it is used -
1592 6. If a program named "hgmerge" can be found on the system, it is used -
1592 but it will by default not be used for symlinks and binary files.
1593 but it will by default not be used for symlinks and binary files.
1593 7. If the file to be merged is not binary and is not a symlink, then
1594 7. If the file to be merged is not binary and is not a symlink, then
1594 internal ":merge" is used.
1595 internal ":merge" is used.
1595 8. The merge of the file fails and must be resolved before commit.
1596 8. The merge of the file fails and must be resolved before commit.
1596
1597
1597 Note:
1598 Note:
1598 After selecting a merge program, Mercurial will by default attempt to
1599 After selecting a merge program, Mercurial will by default attempt to
1599 merge the files using a simple merge algorithm first. Only if it
1600 merge the files using a simple merge algorithm first. Only if it
1600 doesn't succeed because of conflicting changes Mercurial will actually
1601 doesn't succeed because of conflicting changes Mercurial will actually
1601 execute the merge program. Whether to use the simple merge algorithm
1602 execute the merge program. Whether to use the simple merge algorithm
1602 first can be controlled by the premerge setting of the merge tool.
1603 first can be controlled by the premerge setting of the merge tool.
1603 Premerge is enabled by default unless the file is binary or a symlink.
1604 Premerge is enabled by default unless the file is binary or a symlink.
1604
1605
1605 See the merge-tools and ui sections of hgrc(5) for details on the
1606 See the merge-tools and ui sections of hgrc(5) for details on the
1606 configuration of merge tools.
1607 configuration of merge tools.
1607
1608
1608 Test usage of section marks in help documents
1609 Test usage of section marks in help documents
1609
1610
1610 $ cd "$TESTDIR"/../doc
1611 $ cd "$TESTDIR"/../doc
1611 $ python check-seclevel.py
1612 $ python check-seclevel.py
1612 $ cd $TESTTMP
1613 $ cd $TESTTMP
1613
1614
1614 #if serve
1615 #if serve
1615
1616
1616 Test the help pages in hgweb.
1617 Test the help pages in hgweb.
1617
1618
1618 Dish up an empty repo; serve it cold.
1619 Dish up an empty repo; serve it cold.
1619
1620
1620 $ hg init "$TESTTMP/test"
1621 $ hg init "$TESTTMP/test"
1621 $ hg serve -R "$TESTTMP/test" -n test -p $HGPORT -d --pid-file=hg.pid
1622 $ hg serve -R "$TESTTMP/test" -n test -p $HGPORT -d --pid-file=hg.pid
1622 $ cat hg.pid >> $DAEMON_PIDS
1623 $ cat hg.pid >> $DAEMON_PIDS
1623
1624
1624 $ get-with-headers.py 127.0.0.1:$HGPORT "help"
1625 $ get-with-headers.py 127.0.0.1:$HGPORT "help"
1625 200 Script output follows
1626 200 Script output follows
1626
1627
1627 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
1628 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
1628 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
1629 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
1629 <head>
1630 <head>
1630 <link rel="icon" href="/static/hgicon.png" type="image/png" />
1631 <link rel="icon" href="/static/hgicon.png" type="image/png" />
1631 <meta name="robots" content="index, nofollow" />
1632 <meta name="robots" content="index, nofollow" />
1632 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
1633 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
1633 <script type="text/javascript" src="/static/mercurial.js"></script>
1634 <script type="text/javascript" src="/static/mercurial.js"></script>
1634
1635
1635 <title>Help: Index</title>
1636 <title>Help: Index</title>
1636 </head>
1637 </head>
1637 <body>
1638 <body>
1638
1639
1639 <div class="container">
1640 <div class="container">
1640 <div class="menu">
1641 <div class="menu">
1641 <div class="logo">
1642 <div class="logo">
1642 <a href="https://mercurial-scm.org/">
1643 <a href="https://mercurial-scm.org/">
1643 <img src="/static/hglogo.png" alt="mercurial" /></a>
1644 <img src="/static/hglogo.png" alt="mercurial" /></a>
1644 </div>
1645 </div>
1645 <ul>
1646 <ul>
1646 <li><a href="/shortlog">log</a></li>
1647 <li><a href="/shortlog">log</a></li>
1647 <li><a href="/graph">graph</a></li>
1648 <li><a href="/graph">graph</a></li>
1648 <li><a href="/tags">tags</a></li>
1649 <li><a href="/tags">tags</a></li>
1649 <li><a href="/bookmarks">bookmarks</a></li>
1650 <li><a href="/bookmarks">bookmarks</a></li>
1650 <li><a href="/branches">branches</a></li>
1651 <li><a href="/branches">branches</a></li>
1651 </ul>
1652 </ul>
1652 <ul>
1653 <ul>
1653 <li class="active">help</li>
1654 <li class="active">help</li>
1654 </ul>
1655 </ul>
1655 </div>
1656 </div>
1656
1657
1657 <div class="main">
1658 <div class="main">
1658 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
1659 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
1659 <form class="search" action="/log">
1660 <form class="search" action="/log">
1660
1661
1661 <p><input name="rev" id="search1" type="text" size="30" /></p>
1662 <p><input name="rev" id="search1" type="text" size="30" /></p>
1662 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
1663 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
1663 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
1664 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
1664 </form>
1665 </form>
1665 <table class="bigtable">
1666 <table class="bigtable">
1666 <tr><td colspan="2"><h2><a name="main" href="#topics">Topics</a></h2></td></tr>
1667 <tr><td colspan="2"><h2><a name="main" href="#topics">Topics</a></h2></td></tr>
1667
1668
1668 <tr><td>
1669 <tr><td>
1669 <a href="/help/config">
1670 <a href="/help/config">
1670 config
1671 config
1671 </a>
1672 </a>
1672 </td><td>
1673 </td><td>
1673 Configuration Files
1674 Configuration Files
1674 </td></tr>
1675 </td></tr>
1675 <tr><td>
1676 <tr><td>
1676 <a href="/help/dates">
1677 <a href="/help/dates">
1677 dates
1678 dates
1678 </a>
1679 </a>
1679 </td><td>
1680 </td><td>
1680 Date Formats
1681 Date Formats
1681 </td></tr>
1682 </td></tr>
1682 <tr><td>
1683 <tr><td>
1683 <a href="/help/diffs">
1684 <a href="/help/diffs">
1684 diffs
1685 diffs
1685 </a>
1686 </a>
1686 </td><td>
1687 </td><td>
1687 Diff Formats
1688 Diff Formats
1688 </td></tr>
1689 </td></tr>
1689 <tr><td>
1690 <tr><td>
1690 <a href="/help/environment">
1691 <a href="/help/environment">
1691 environment
1692 environment
1692 </a>
1693 </a>
1693 </td><td>
1694 </td><td>
1694 Environment Variables
1695 Environment Variables
1695 </td></tr>
1696 </td></tr>
1696 <tr><td>
1697 <tr><td>
1697 <a href="/help/extensions">
1698 <a href="/help/extensions">
1698 extensions
1699 extensions
1699 </a>
1700 </a>
1700 </td><td>
1701 </td><td>
1701 Using Additional Features
1702 Using Additional Features
1702 </td></tr>
1703 </td></tr>
1703 <tr><td>
1704 <tr><td>
1704 <a href="/help/filesets">
1705 <a href="/help/filesets">
1705 filesets
1706 filesets
1706 </a>
1707 </a>
1707 </td><td>
1708 </td><td>
1708 Specifying File Sets
1709 Specifying File Sets
1709 </td></tr>
1710 </td></tr>
1710 <tr><td>
1711 <tr><td>
1711 <a href="/help/glossary">
1712 <a href="/help/glossary">
1712 glossary
1713 glossary
1713 </a>
1714 </a>
1714 </td><td>
1715 </td><td>
1715 Glossary
1716 Glossary
1716 </td></tr>
1717 </td></tr>
1717 <tr><td>
1718 <tr><td>
1718 <a href="/help/hgignore">
1719 <a href="/help/hgignore">
1719 hgignore
1720 hgignore
1720 </a>
1721 </a>
1721 </td><td>
1722 </td><td>
1722 Syntax for Mercurial Ignore Files
1723 Syntax for Mercurial Ignore Files
1723 </td></tr>
1724 </td></tr>
1724 <tr><td>
1725 <tr><td>
1725 <a href="/help/hgweb">
1726 <a href="/help/hgweb">
1726 hgweb
1727 hgweb
1727 </a>
1728 </a>
1728 </td><td>
1729 </td><td>
1729 Configuring hgweb
1730 Configuring hgweb
1730 </td></tr>
1731 </td></tr>
1731 <tr><td>
1732 <tr><td>
1732 <a href="/help/internals">
1733 <a href="/help/internals">
1733 internals
1734 internals
1734 </a>
1735 </a>
1735 </td><td>
1736 </td><td>
1736 Technical implementation topics
1737 Technical implementation topics
1737 </td></tr>
1738 </td></tr>
1738 <tr><td>
1739 <tr><td>
1739 <a href="/help/merge-tools">
1740 <a href="/help/merge-tools">
1740 merge-tools
1741 merge-tools
1741 </a>
1742 </a>
1742 </td><td>
1743 </td><td>
1743 Merge Tools
1744 Merge Tools
1744 </td></tr>
1745 </td></tr>
1745 <tr><td>
1746 <tr><td>
1746 <a href="/help/multirevs">
1747 <a href="/help/multirevs">
1747 multirevs
1748 multirevs
1748 </a>
1749 </a>
1749 </td><td>
1750 </td><td>
1750 Specifying Multiple Revisions
1751 Specifying Multiple Revisions
1751 </td></tr>
1752 </td></tr>
1752 <tr><td>
1753 <tr><td>
1753 <a href="/help/patterns">
1754 <a href="/help/patterns">
1754 patterns
1755 patterns
1755 </a>
1756 </a>
1756 </td><td>
1757 </td><td>
1757 File Name Patterns
1758 File Name Patterns
1758 </td></tr>
1759 </td></tr>
1759 <tr><td>
1760 <tr><td>
1760 <a href="/help/phases">
1761 <a href="/help/phases">
1761 phases
1762 phases
1762 </a>
1763 </a>
1763 </td><td>
1764 </td><td>
1764 Working with Phases
1765 Working with Phases
1765 </td></tr>
1766 </td></tr>
1766 <tr><td>
1767 <tr><td>
1767 <a href="/help/revisions">
1768 <a href="/help/revisions">
1768 revisions
1769 revisions
1769 </a>
1770 </a>
1770 </td><td>
1771 </td><td>
1771 Specifying Single Revisions
1772 Specifying Single Revisions
1772 </td></tr>
1773 </td></tr>
1773 <tr><td>
1774 <tr><td>
1774 <a href="/help/revsets">
1775 <a href="/help/revsets">
1775 revsets
1776 revsets
1776 </a>
1777 </a>
1777 </td><td>
1778 </td><td>
1778 Specifying Revision Sets
1779 Specifying Revision Sets
1779 </td></tr>
1780 </td></tr>
1780 <tr><td>
1781 <tr><td>
1781 <a href="/help/scripting">
1782 <a href="/help/scripting">
1782 scripting
1783 scripting
1783 </a>
1784 </a>
1784 </td><td>
1785 </td><td>
1785 Using Mercurial from scripts and automation
1786 Using Mercurial from scripts and automation
1786 </td></tr>
1787 </td></tr>
1787 <tr><td>
1788 <tr><td>
1788 <a href="/help/subrepos">
1789 <a href="/help/subrepos">
1789 subrepos
1790 subrepos
1790 </a>
1791 </a>
1791 </td><td>
1792 </td><td>
1792 Subrepositories
1793 Subrepositories
1793 </td></tr>
1794 </td></tr>
1794 <tr><td>
1795 <tr><td>
1795 <a href="/help/templating">
1796 <a href="/help/templating">
1796 templating
1797 templating
1797 </a>
1798 </a>
1798 </td><td>
1799 </td><td>
1799 Template Usage
1800 Template Usage
1800 </td></tr>
1801 </td></tr>
1801 <tr><td>
1802 <tr><td>
1802 <a href="/help/urls">
1803 <a href="/help/urls">
1803 urls
1804 urls
1804 </a>
1805 </a>
1805 </td><td>
1806 </td><td>
1806 URL Paths
1807 URL Paths
1807 </td></tr>
1808 </td></tr>
1808 <tr><td>
1809 <tr><td>
1809 <a href="/help/topic-containing-verbose">
1810 <a href="/help/topic-containing-verbose">
1810 topic-containing-verbose
1811 topic-containing-verbose
1811 </a>
1812 </a>
1812 </td><td>
1813 </td><td>
1813 This is the topic to test omit indicating.
1814 This is the topic to test omit indicating.
1814 </td></tr>
1815 </td></tr>
1815
1816
1816
1817
1817 <tr><td colspan="2"><h2><a name="main" href="#main">Main Commands</a></h2></td></tr>
1818 <tr><td colspan="2"><h2><a name="main" href="#main">Main Commands</a></h2></td></tr>
1818
1819
1819 <tr><td>
1820 <tr><td>
1820 <a href="/help/add">
1821 <a href="/help/add">
1821 add
1822 add
1822 </a>
1823 </a>
1823 </td><td>
1824 </td><td>
1824 add the specified files on the next commit
1825 add the specified files on the next commit
1825 </td></tr>
1826 </td></tr>
1826 <tr><td>
1827 <tr><td>
1827 <a href="/help/annotate">
1828 <a href="/help/annotate">
1828 annotate
1829 annotate
1829 </a>
1830 </a>
1830 </td><td>
1831 </td><td>
1831 show changeset information by line for each file
1832 show changeset information by line for each file
1832 </td></tr>
1833 </td></tr>
1833 <tr><td>
1834 <tr><td>
1834 <a href="/help/clone">
1835 <a href="/help/clone">
1835 clone
1836 clone
1836 </a>
1837 </a>
1837 </td><td>
1838 </td><td>
1838 make a copy of an existing repository
1839 make a copy of an existing repository
1839 </td></tr>
1840 </td></tr>
1840 <tr><td>
1841 <tr><td>
1841 <a href="/help/commit">
1842 <a href="/help/commit">
1842 commit
1843 commit
1843 </a>
1844 </a>
1844 </td><td>
1845 </td><td>
1845 commit the specified files or all outstanding changes
1846 commit the specified files or all outstanding changes
1846 </td></tr>
1847 </td></tr>
1847 <tr><td>
1848 <tr><td>
1848 <a href="/help/diff">
1849 <a href="/help/diff">
1849 diff
1850 diff
1850 </a>
1851 </a>
1851 </td><td>
1852 </td><td>
1852 diff repository (or selected files)
1853 diff repository (or selected files)
1853 </td></tr>
1854 </td></tr>
1854 <tr><td>
1855 <tr><td>
1855 <a href="/help/export">
1856 <a href="/help/export">
1856 export
1857 export
1857 </a>
1858 </a>
1858 </td><td>
1859 </td><td>
1859 dump the header and diffs for one or more changesets
1860 dump the header and diffs for one or more changesets
1860 </td></tr>
1861 </td></tr>
1861 <tr><td>
1862 <tr><td>
1862 <a href="/help/forget">
1863 <a href="/help/forget">
1863 forget
1864 forget
1864 </a>
1865 </a>
1865 </td><td>
1866 </td><td>
1866 forget the specified files on the next commit
1867 forget the specified files on the next commit
1867 </td></tr>
1868 </td></tr>
1868 <tr><td>
1869 <tr><td>
1869 <a href="/help/init">
1870 <a href="/help/init">
1870 init
1871 init
1871 </a>
1872 </a>
1872 </td><td>
1873 </td><td>
1873 create a new repository in the given directory
1874 create a new repository in the given directory
1874 </td></tr>
1875 </td></tr>
1875 <tr><td>
1876 <tr><td>
1876 <a href="/help/log">
1877 <a href="/help/log">
1877 log
1878 log
1878 </a>
1879 </a>
1879 </td><td>
1880 </td><td>
1880 show revision history of entire repository or files
1881 show revision history of entire repository or files
1881 </td></tr>
1882 </td></tr>
1882 <tr><td>
1883 <tr><td>
1883 <a href="/help/merge">
1884 <a href="/help/merge">
1884 merge
1885 merge
1885 </a>
1886 </a>
1886 </td><td>
1887 </td><td>
1887 merge another revision into working directory
1888 merge another revision into working directory
1888 </td></tr>
1889 </td></tr>
1889 <tr><td>
1890 <tr><td>
1890 <a href="/help/pull">
1891 <a href="/help/pull">
1891 pull
1892 pull
1892 </a>
1893 </a>
1893 </td><td>
1894 </td><td>
1894 pull changes from the specified source
1895 pull changes from the specified source
1895 </td></tr>
1896 </td></tr>
1896 <tr><td>
1897 <tr><td>
1897 <a href="/help/push">
1898 <a href="/help/push">
1898 push
1899 push
1899 </a>
1900 </a>
1900 </td><td>
1901 </td><td>
1901 push changes to the specified destination
1902 push changes to the specified destination
1902 </td></tr>
1903 </td></tr>
1903 <tr><td>
1904 <tr><td>
1904 <a href="/help/remove">
1905 <a href="/help/remove">
1905 remove
1906 remove
1906 </a>
1907 </a>
1907 </td><td>
1908 </td><td>
1908 remove the specified files on the next commit
1909 remove the specified files on the next commit
1909 </td></tr>
1910 </td></tr>
1910 <tr><td>
1911 <tr><td>
1911 <a href="/help/serve">
1912 <a href="/help/serve">
1912 serve
1913 serve
1913 </a>
1914 </a>
1914 </td><td>
1915 </td><td>
1915 start stand-alone webserver
1916 start stand-alone webserver
1916 </td></tr>
1917 </td></tr>
1917 <tr><td>
1918 <tr><td>
1918 <a href="/help/status">
1919 <a href="/help/status">
1919 status
1920 status
1920 </a>
1921 </a>
1921 </td><td>
1922 </td><td>
1922 show changed files in the working directory
1923 show changed files in the working directory
1923 </td></tr>
1924 </td></tr>
1924 <tr><td>
1925 <tr><td>
1925 <a href="/help/summary">
1926 <a href="/help/summary">
1926 summary
1927 summary
1927 </a>
1928 </a>
1928 </td><td>
1929 </td><td>
1929 summarize working directory state
1930 summarize working directory state
1930 </td></tr>
1931 </td></tr>
1931 <tr><td>
1932 <tr><td>
1932 <a href="/help/update">
1933 <a href="/help/update">
1933 update
1934 update
1934 </a>
1935 </a>
1935 </td><td>
1936 </td><td>
1936 update working directory (or switch revisions)
1937 update working directory (or switch revisions)
1937 </td></tr>
1938 </td></tr>
1938
1939
1939
1940
1940
1941
1941 <tr><td colspan="2"><h2><a name="other" href="#other">Other Commands</a></h2></td></tr>
1942 <tr><td colspan="2"><h2><a name="other" href="#other">Other Commands</a></h2></td></tr>
1942
1943
1943 <tr><td>
1944 <tr><td>
1944 <a href="/help/addremove">
1945 <a href="/help/addremove">
1945 addremove
1946 addremove
1946 </a>
1947 </a>
1947 </td><td>
1948 </td><td>
1948 add all new files, delete all missing files
1949 add all new files, delete all missing files
1949 </td></tr>
1950 </td></tr>
1950 <tr><td>
1951 <tr><td>
1951 <a href="/help/archive">
1952 <a href="/help/archive">
1952 archive
1953 archive
1953 </a>
1954 </a>
1954 </td><td>
1955 </td><td>
1955 create an unversioned archive of a repository revision
1956 create an unversioned archive of a repository revision
1956 </td></tr>
1957 </td></tr>
1957 <tr><td>
1958 <tr><td>
1958 <a href="/help/backout">
1959 <a href="/help/backout">
1959 backout
1960 backout
1960 </a>
1961 </a>
1961 </td><td>
1962 </td><td>
1962 reverse effect of earlier changeset
1963 reverse effect of earlier changeset
1963 </td></tr>
1964 </td></tr>
1964 <tr><td>
1965 <tr><td>
1965 <a href="/help/bisect">
1966 <a href="/help/bisect">
1966 bisect
1967 bisect
1967 </a>
1968 </a>
1968 </td><td>
1969 </td><td>
1969 subdivision search of changesets
1970 subdivision search of changesets
1970 </td></tr>
1971 </td></tr>
1971 <tr><td>
1972 <tr><td>
1972 <a href="/help/bookmarks">
1973 <a href="/help/bookmarks">
1973 bookmarks
1974 bookmarks
1974 </a>
1975 </a>
1975 </td><td>
1976 </td><td>
1976 create a new bookmark or list existing bookmarks
1977 create a new bookmark or list existing bookmarks
1977 </td></tr>
1978 </td></tr>
1978 <tr><td>
1979 <tr><td>
1979 <a href="/help/branch">
1980 <a href="/help/branch">
1980 branch
1981 branch
1981 </a>
1982 </a>
1982 </td><td>
1983 </td><td>
1983 set or show the current branch name
1984 set or show the current branch name
1984 </td></tr>
1985 </td></tr>
1985 <tr><td>
1986 <tr><td>
1986 <a href="/help/branches">
1987 <a href="/help/branches">
1987 branches
1988 branches
1988 </a>
1989 </a>
1989 </td><td>
1990 </td><td>
1990 list repository named branches
1991 list repository named branches
1991 </td></tr>
1992 </td></tr>
1992 <tr><td>
1993 <tr><td>
1993 <a href="/help/bundle">
1994 <a href="/help/bundle">
1994 bundle
1995 bundle
1995 </a>
1996 </a>
1996 </td><td>
1997 </td><td>
1997 create a changegroup file
1998 create a changegroup file
1998 </td></tr>
1999 </td></tr>
1999 <tr><td>
2000 <tr><td>
2000 <a href="/help/cat">
2001 <a href="/help/cat">
2001 cat
2002 cat
2002 </a>
2003 </a>
2003 </td><td>
2004 </td><td>
2004 output the current or given revision of files
2005 output the current or given revision of files
2005 </td></tr>
2006 </td></tr>
2006 <tr><td>
2007 <tr><td>
2007 <a href="/help/config">
2008 <a href="/help/config">
2008 config
2009 config
2009 </a>
2010 </a>
2010 </td><td>
2011 </td><td>
2011 show combined config settings from all hgrc files
2012 show combined config settings from all hgrc files
2012 </td></tr>
2013 </td></tr>
2013 <tr><td>
2014 <tr><td>
2014 <a href="/help/copy">
2015 <a href="/help/copy">
2015 copy
2016 copy
2016 </a>
2017 </a>
2017 </td><td>
2018 </td><td>
2018 mark files as copied for the next commit
2019 mark files as copied for the next commit
2019 </td></tr>
2020 </td></tr>
2020 <tr><td>
2021 <tr><td>
2021 <a href="/help/files">
2022 <a href="/help/files">
2022 files
2023 files
2023 </a>
2024 </a>
2024 </td><td>
2025 </td><td>
2025 list tracked files
2026 list tracked files
2026 </td></tr>
2027 </td></tr>
2027 <tr><td>
2028 <tr><td>
2028 <a href="/help/graft">
2029 <a href="/help/graft">
2029 graft
2030 graft
2030 </a>
2031 </a>
2031 </td><td>
2032 </td><td>
2032 copy changes from other branches onto the current branch
2033 copy changes from other branches onto the current branch
2033 </td></tr>
2034 </td></tr>
2034 <tr><td>
2035 <tr><td>
2035 <a href="/help/grep">
2036 <a href="/help/grep">
2036 grep
2037 grep
2037 </a>
2038 </a>
2038 </td><td>
2039 </td><td>
2039 search for a pattern in specified files and revisions
2040 search for a pattern in specified files and revisions
2040 </td></tr>
2041 </td></tr>
2041 <tr><td>
2042 <tr><td>
2042 <a href="/help/heads">
2043 <a href="/help/heads">
2043 heads
2044 heads
2044 </a>
2045 </a>
2045 </td><td>
2046 </td><td>
2046 show branch heads
2047 show branch heads
2047 </td></tr>
2048 </td></tr>
2048 <tr><td>
2049 <tr><td>
2049 <a href="/help/help">
2050 <a href="/help/help">
2050 help
2051 help
2051 </a>
2052 </a>
2052 </td><td>
2053 </td><td>
2053 show help for a given topic or a help overview
2054 show help for a given topic or a help overview
2054 </td></tr>
2055 </td></tr>
2055 <tr><td>
2056 <tr><td>
2056 <a href="/help/identify">
2057 <a href="/help/identify">
2057 identify
2058 identify
2058 </a>
2059 </a>
2059 </td><td>
2060 </td><td>
2060 identify the working directory or specified revision
2061 identify the working directory or specified revision
2061 </td></tr>
2062 </td></tr>
2062 <tr><td>
2063 <tr><td>
2063 <a href="/help/import">
2064 <a href="/help/import">
2064 import
2065 import
2065 </a>
2066 </a>
2066 </td><td>
2067 </td><td>
2067 import an ordered set of patches
2068 import an ordered set of patches
2068 </td></tr>
2069 </td></tr>
2069 <tr><td>
2070 <tr><td>
2070 <a href="/help/incoming">
2071 <a href="/help/incoming">
2071 incoming
2072 incoming
2072 </a>
2073 </a>
2073 </td><td>
2074 </td><td>
2074 show new changesets found in source
2075 show new changesets found in source
2075 </td></tr>
2076 </td></tr>
2076 <tr><td>
2077 <tr><td>
2077 <a href="/help/manifest">
2078 <a href="/help/manifest">
2078 manifest
2079 manifest
2079 </a>
2080 </a>
2080 </td><td>
2081 </td><td>
2081 output the current or given revision of the project manifest
2082 output the current or given revision of the project manifest
2082 </td></tr>
2083 </td></tr>
2083 <tr><td>
2084 <tr><td>
2084 <a href="/help/nohelp">
2085 <a href="/help/nohelp">
2085 nohelp
2086 nohelp
2086 </a>
2087 </a>
2087 </td><td>
2088 </td><td>
2088 (no help text available)
2089 (no help text available)
2089 </td></tr>
2090 </td></tr>
2090 <tr><td>
2091 <tr><td>
2091 <a href="/help/outgoing">
2092 <a href="/help/outgoing">
2092 outgoing
2093 outgoing
2093 </a>
2094 </a>
2094 </td><td>
2095 </td><td>
2095 show changesets not found in the destination
2096 show changesets not found in the destination
2096 </td></tr>
2097 </td></tr>
2097 <tr><td>
2098 <tr><td>
2098 <a href="/help/paths">
2099 <a href="/help/paths">
2099 paths
2100 paths
2100 </a>
2101 </a>
2101 </td><td>
2102 </td><td>
2102 show aliases for remote repositories
2103 show aliases for remote repositories
2103 </td></tr>
2104 </td></tr>
2104 <tr><td>
2105 <tr><td>
2105 <a href="/help/phase">
2106 <a href="/help/phase">
2106 phase
2107 phase
2107 </a>
2108 </a>
2108 </td><td>
2109 </td><td>
2109 set or show the current phase name
2110 set or show the current phase name
2110 </td></tr>
2111 </td></tr>
2111 <tr><td>
2112 <tr><td>
2112 <a href="/help/recover">
2113 <a href="/help/recover">
2113 recover
2114 recover
2114 </a>
2115 </a>
2115 </td><td>
2116 </td><td>
2116 roll back an interrupted transaction
2117 roll back an interrupted transaction
2117 </td></tr>
2118 </td></tr>
2118 <tr><td>
2119 <tr><td>
2119 <a href="/help/rename">
2120 <a href="/help/rename">
2120 rename
2121 rename
2121 </a>
2122 </a>
2122 </td><td>
2123 </td><td>
2123 rename files; equivalent of copy + remove
2124 rename files; equivalent of copy + remove
2124 </td></tr>
2125 </td></tr>
2125 <tr><td>
2126 <tr><td>
2126 <a href="/help/resolve">
2127 <a href="/help/resolve">
2127 resolve
2128 resolve
2128 </a>
2129 </a>
2129 </td><td>
2130 </td><td>
2130 redo merges or set/view the merge status of files
2131 redo merges or set/view the merge status of files
2131 </td></tr>
2132 </td></tr>
2132 <tr><td>
2133 <tr><td>
2133 <a href="/help/revert">
2134 <a href="/help/revert">
2134 revert
2135 revert
2135 </a>
2136 </a>
2136 </td><td>
2137 </td><td>
2137 restore files to their checkout state
2138 restore files to their checkout state
2138 </td></tr>
2139 </td></tr>
2139 <tr><td>
2140 <tr><td>
2140 <a href="/help/root">
2141 <a href="/help/root">
2141 root
2142 root
2142 </a>
2143 </a>
2143 </td><td>
2144 </td><td>
2144 print the root (top) of the current working directory
2145 print the root (top) of the current working directory
2145 </td></tr>
2146 </td></tr>
2146 <tr><td>
2147 <tr><td>
2147 <a href="/help/tag">
2148 <a href="/help/tag">
2148 tag
2149 tag
2149 </a>
2150 </a>
2150 </td><td>
2151 </td><td>
2151 add one or more tags for the current or given revision
2152 add one or more tags for the current or given revision
2152 </td></tr>
2153 </td></tr>
2153 <tr><td>
2154 <tr><td>
2154 <a href="/help/tags">
2155 <a href="/help/tags">
2155 tags
2156 tags
2156 </a>
2157 </a>
2157 </td><td>
2158 </td><td>
2158 list repository tags
2159 list repository tags
2159 </td></tr>
2160 </td></tr>
2160 <tr><td>
2161 <tr><td>
2161 <a href="/help/unbundle">
2162 <a href="/help/unbundle">
2162 unbundle
2163 unbundle
2163 </a>
2164 </a>
2164 </td><td>
2165 </td><td>
2165 apply one or more changegroup files
2166 apply one or more changegroup files
2166 </td></tr>
2167 </td></tr>
2167 <tr><td>
2168 <tr><td>
2168 <a href="/help/verify">
2169 <a href="/help/verify">
2169 verify
2170 verify
2170 </a>
2171 </a>
2171 </td><td>
2172 </td><td>
2172 verify the integrity of the repository
2173 verify the integrity of the repository
2173 </td></tr>
2174 </td></tr>
2174 <tr><td>
2175 <tr><td>
2175 <a href="/help/version">
2176 <a href="/help/version">
2176 version
2177 version
2177 </a>
2178 </a>
2178 </td><td>
2179 </td><td>
2179 output version and copyright information
2180 output version and copyright information
2180 </td></tr>
2181 </td></tr>
2181
2182
2182
2183
2183 </table>
2184 </table>
2184 </div>
2185 </div>
2185 </div>
2186 </div>
2186
2187
2187 <script type="text/javascript">process_dates()</script>
2188 <script type="text/javascript">process_dates()</script>
2188
2189
2189
2190
2190 </body>
2191 </body>
2191 </html>
2192 </html>
2192
2193
2193
2194
2194 $ get-with-headers.py 127.0.0.1:$HGPORT "help/add"
2195 $ get-with-headers.py 127.0.0.1:$HGPORT "help/add"
2195 200 Script output follows
2196 200 Script output follows
2196
2197
2197 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2198 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2198 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2199 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2199 <head>
2200 <head>
2200 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2201 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2201 <meta name="robots" content="index, nofollow" />
2202 <meta name="robots" content="index, nofollow" />
2202 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2203 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2203 <script type="text/javascript" src="/static/mercurial.js"></script>
2204 <script type="text/javascript" src="/static/mercurial.js"></script>
2204
2205
2205 <title>Help: add</title>
2206 <title>Help: add</title>
2206 </head>
2207 </head>
2207 <body>
2208 <body>
2208
2209
2209 <div class="container">
2210 <div class="container">
2210 <div class="menu">
2211 <div class="menu">
2211 <div class="logo">
2212 <div class="logo">
2212 <a href="https://mercurial-scm.org/">
2213 <a href="https://mercurial-scm.org/">
2213 <img src="/static/hglogo.png" alt="mercurial" /></a>
2214 <img src="/static/hglogo.png" alt="mercurial" /></a>
2214 </div>
2215 </div>
2215 <ul>
2216 <ul>
2216 <li><a href="/shortlog">log</a></li>
2217 <li><a href="/shortlog">log</a></li>
2217 <li><a href="/graph">graph</a></li>
2218 <li><a href="/graph">graph</a></li>
2218 <li><a href="/tags">tags</a></li>
2219 <li><a href="/tags">tags</a></li>
2219 <li><a href="/bookmarks">bookmarks</a></li>
2220 <li><a href="/bookmarks">bookmarks</a></li>
2220 <li><a href="/branches">branches</a></li>
2221 <li><a href="/branches">branches</a></li>
2221 </ul>
2222 </ul>
2222 <ul>
2223 <ul>
2223 <li class="active"><a href="/help">help</a></li>
2224 <li class="active"><a href="/help">help</a></li>
2224 </ul>
2225 </ul>
2225 </div>
2226 </div>
2226
2227
2227 <div class="main">
2228 <div class="main">
2228 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2229 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2229 <h3>Help: add</h3>
2230 <h3>Help: add</h3>
2230
2231
2231 <form class="search" action="/log">
2232 <form class="search" action="/log">
2232
2233
2233 <p><input name="rev" id="search1" type="text" size="30" /></p>
2234 <p><input name="rev" id="search1" type="text" size="30" /></p>
2234 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2235 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2235 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2236 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2236 </form>
2237 </form>
2237 <div id="doc">
2238 <div id="doc">
2238 <p>
2239 <p>
2239 hg add [OPTION]... [FILE]...
2240 hg add [OPTION]... [FILE]...
2240 </p>
2241 </p>
2241 <p>
2242 <p>
2242 add the specified files on the next commit
2243 add the specified files on the next commit
2243 </p>
2244 </p>
2244 <p>
2245 <p>
2245 Schedule files to be version controlled and added to the
2246 Schedule files to be version controlled and added to the
2246 repository.
2247 repository.
2247 </p>
2248 </p>
2248 <p>
2249 <p>
2249 The files will be added to the repository at the next commit. To
2250 The files will be added to the repository at the next commit. To
2250 undo an add before that, see &quot;hg forget&quot;.
2251 undo an add before that, see &quot;hg forget&quot;.
2251 </p>
2252 </p>
2252 <p>
2253 <p>
2253 If no names are given, add all files to the repository (except
2254 If no names are given, add all files to the repository (except
2254 files matching &quot;.hgignore&quot;).
2255 files matching &quot;.hgignore&quot;).
2255 </p>
2256 </p>
2256 <p>
2257 <p>
2257 Examples:
2258 Examples:
2258 </p>
2259 </p>
2259 <ul>
2260 <ul>
2260 <li> New (unknown) files are added automatically by &quot;hg add&quot;:
2261 <li> New (unknown) files are added automatically by &quot;hg add&quot;:
2261 <pre>
2262 <pre>
2262 \$ ls (re)
2263 \$ ls (re)
2263 foo.c
2264 foo.c
2264 \$ hg status (re)
2265 \$ hg status (re)
2265 ? foo.c
2266 ? foo.c
2266 \$ hg add (re)
2267 \$ hg add (re)
2267 adding foo.c
2268 adding foo.c
2268 \$ hg status (re)
2269 \$ hg status (re)
2269 A foo.c
2270 A foo.c
2270 </pre>
2271 </pre>
2271 <li> Specific files to be added can be specified:
2272 <li> Specific files to be added can be specified:
2272 <pre>
2273 <pre>
2273 \$ ls (re)
2274 \$ ls (re)
2274 bar.c foo.c
2275 bar.c foo.c
2275 \$ hg status (re)
2276 \$ hg status (re)
2276 ? bar.c
2277 ? bar.c
2277 ? foo.c
2278 ? foo.c
2278 \$ hg add bar.c (re)
2279 \$ hg add bar.c (re)
2279 \$ hg status (re)
2280 \$ hg status (re)
2280 A bar.c
2281 A bar.c
2281 ? foo.c
2282 ? foo.c
2282 </pre>
2283 </pre>
2283 </ul>
2284 </ul>
2284 <p>
2285 <p>
2285 Returns 0 if all files are successfully added.
2286 Returns 0 if all files are successfully added.
2286 </p>
2287 </p>
2287 <p>
2288 <p>
2288 options ([+] can be repeated):
2289 options ([+] can be repeated):
2289 </p>
2290 </p>
2290 <table>
2291 <table>
2291 <tr><td>-I</td>
2292 <tr><td>-I</td>
2292 <td>--include PATTERN [+]</td>
2293 <td>--include PATTERN [+]</td>
2293 <td>include names matching the given patterns</td></tr>
2294 <td>include names matching the given patterns</td></tr>
2294 <tr><td>-X</td>
2295 <tr><td>-X</td>
2295 <td>--exclude PATTERN [+]</td>
2296 <td>--exclude PATTERN [+]</td>
2296 <td>exclude names matching the given patterns</td></tr>
2297 <td>exclude names matching the given patterns</td></tr>
2297 <tr><td>-S</td>
2298 <tr><td>-S</td>
2298 <td>--subrepos</td>
2299 <td>--subrepos</td>
2299 <td>recurse into subrepositories</td></tr>
2300 <td>recurse into subrepositories</td></tr>
2300 <tr><td>-n</td>
2301 <tr><td>-n</td>
2301 <td>--dry-run</td>
2302 <td>--dry-run</td>
2302 <td>do not perform actions, just print output</td></tr>
2303 <td>do not perform actions, just print output</td></tr>
2303 </table>
2304 </table>
2304 <p>
2305 <p>
2305 global options ([+] can be repeated):
2306 global options ([+] can be repeated):
2306 </p>
2307 </p>
2307 <table>
2308 <table>
2308 <tr><td>-R</td>
2309 <tr><td>-R</td>
2309 <td>--repository REPO</td>
2310 <td>--repository REPO</td>
2310 <td>repository root directory or name of overlay bundle file</td></tr>
2311 <td>repository root directory or name of overlay bundle file</td></tr>
2311 <tr><td></td>
2312 <tr><td></td>
2312 <td>--cwd DIR</td>
2313 <td>--cwd DIR</td>
2313 <td>change working directory</td></tr>
2314 <td>change working directory</td></tr>
2314 <tr><td>-y</td>
2315 <tr><td>-y</td>
2315 <td>--noninteractive</td>
2316 <td>--noninteractive</td>
2316 <td>do not prompt, automatically pick the first choice for all prompts</td></tr>
2317 <td>do not prompt, automatically pick the first choice for all prompts</td></tr>
2317 <tr><td>-q</td>
2318 <tr><td>-q</td>
2318 <td>--quiet</td>
2319 <td>--quiet</td>
2319 <td>suppress output</td></tr>
2320 <td>suppress output</td></tr>
2320 <tr><td>-v</td>
2321 <tr><td>-v</td>
2321 <td>--verbose</td>
2322 <td>--verbose</td>
2322 <td>enable additional output</td></tr>
2323 <td>enable additional output</td></tr>
2323 <tr><td></td>
2324 <tr><td></td>
2324 <td>--config CONFIG [+]</td>
2325 <td>--config CONFIG [+]</td>
2325 <td>set/override config option (use 'section.name=value')</td></tr>
2326 <td>set/override config option (use 'section.name=value')</td></tr>
2326 <tr><td></td>
2327 <tr><td></td>
2327 <td>--debug</td>
2328 <td>--debug</td>
2328 <td>enable debugging output</td></tr>
2329 <td>enable debugging output</td></tr>
2329 <tr><td></td>
2330 <tr><td></td>
2330 <td>--debugger</td>
2331 <td>--debugger</td>
2331 <td>start debugger</td></tr>
2332 <td>start debugger</td></tr>
2332 <tr><td></td>
2333 <tr><td></td>
2333 <td>--encoding ENCODE</td>
2334 <td>--encoding ENCODE</td>
2334 <td>set the charset encoding (default: ascii)</td></tr>
2335 <td>set the charset encoding (default: ascii)</td></tr>
2335 <tr><td></td>
2336 <tr><td></td>
2336 <td>--encodingmode MODE</td>
2337 <td>--encodingmode MODE</td>
2337 <td>set the charset encoding mode (default: strict)</td></tr>
2338 <td>set the charset encoding mode (default: strict)</td></tr>
2338 <tr><td></td>
2339 <tr><td></td>
2339 <td>--traceback</td>
2340 <td>--traceback</td>
2340 <td>always print a traceback on exception</td></tr>
2341 <td>always print a traceback on exception</td></tr>
2341 <tr><td></td>
2342 <tr><td></td>
2342 <td>--time</td>
2343 <td>--time</td>
2343 <td>time how long the command takes</td></tr>
2344 <td>time how long the command takes</td></tr>
2344 <tr><td></td>
2345 <tr><td></td>
2345 <td>--profile</td>
2346 <td>--profile</td>
2346 <td>print command execution profile</td></tr>
2347 <td>print command execution profile</td></tr>
2347 <tr><td></td>
2348 <tr><td></td>
2348 <td>--version</td>
2349 <td>--version</td>
2349 <td>output version information and exit</td></tr>
2350 <td>output version information and exit</td></tr>
2350 <tr><td>-h</td>
2351 <tr><td>-h</td>
2351 <td>--help</td>
2352 <td>--help</td>
2352 <td>display help and exit</td></tr>
2353 <td>display help and exit</td></tr>
2353 <tr><td></td>
2354 <tr><td></td>
2354 <td>--hidden</td>
2355 <td>--hidden</td>
2355 <td>consider hidden changesets</td></tr>
2356 <td>consider hidden changesets</td></tr>
2356 </table>
2357 </table>
2357
2358
2358 </div>
2359 </div>
2359 </div>
2360 </div>
2360 </div>
2361 </div>
2361
2362
2362 <script type="text/javascript">process_dates()</script>
2363 <script type="text/javascript">process_dates()</script>
2363
2364
2364
2365
2365 </body>
2366 </body>
2366 </html>
2367 </html>
2367
2368
2368
2369
2369 $ get-with-headers.py 127.0.0.1:$HGPORT "help/remove"
2370 $ get-with-headers.py 127.0.0.1:$HGPORT "help/remove"
2370 200 Script output follows
2371 200 Script output follows
2371
2372
2372 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2373 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2373 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2374 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2374 <head>
2375 <head>
2375 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2376 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2376 <meta name="robots" content="index, nofollow" />
2377 <meta name="robots" content="index, nofollow" />
2377 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2378 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2378 <script type="text/javascript" src="/static/mercurial.js"></script>
2379 <script type="text/javascript" src="/static/mercurial.js"></script>
2379
2380
2380 <title>Help: remove</title>
2381 <title>Help: remove</title>
2381 </head>
2382 </head>
2382 <body>
2383 <body>
2383
2384
2384 <div class="container">
2385 <div class="container">
2385 <div class="menu">
2386 <div class="menu">
2386 <div class="logo">
2387 <div class="logo">
2387 <a href="https://mercurial-scm.org/">
2388 <a href="https://mercurial-scm.org/">
2388 <img src="/static/hglogo.png" alt="mercurial" /></a>
2389 <img src="/static/hglogo.png" alt="mercurial" /></a>
2389 </div>
2390 </div>
2390 <ul>
2391 <ul>
2391 <li><a href="/shortlog">log</a></li>
2392 <li><a href="/shortlog">log</a></li>
2392 <li><a href="/graph">graph</a></li>
2393 <li><a href="/graph">graph</a></li>
2393 <li><a href="/tags">tags</a></li>
2394 <li><a href="/tags">tags</a></li>
2394 <li><a href="/bookmarks">bookmarks</a></li>
2395 <li><a href="/bookmarks">bookmarks</a></li>
2395 <li><a href="/branches">branches</a></li>
2396 <li><a href="/branches">branches</a></li>
2396 </ul>
2397 </ul>
2397 <ul>
2398 <ul>
2398 <li class="active"><a href="/help">help</a></li>
2399 <li class="active"><a href="/help">help</a></li>
2399 </ul>
2400 </ul>
2400 </div>
2401 </div>
2401
2402
2402 <div class="main">
2403 <div class="main">
2403 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2404 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2404 <h3>Help: remove</h3>
2405 <h3>Help: remove</h3>
2405
2406
2406 <form class="search" action="/log">
2407 <form class="search" action="/log">
2407
2408
2408 <p><input name="rev" id="search1" type="text" size="30" /></p>
2409 <p><input name="rev" id="search1" type="text" size="30" /></p>
2409 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2410 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2410 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2411 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2411 </form>
2412 </form>
2412 <div id="doc">
2413 <div id="doc">
2413 <p>
2414 <p>
2414 hg remove [OPTION]... FILE...
2415 hg remove [OPTION]... FILE...
2415 </p>
2416 </p>
2416 <p>
2417 <p>
2417 aliases: rm
2418 aliases: rm
2418 </p>
2419 </p>
2419 <p>
2420 <p>
2420 remove the specified files on the next commit
2421 remove the specified files on the next commit
2421 </p>
2422 </p>
2422 <p>
2423 <p>
2423 Schedule the indicated files for removal from the current branch.
2424 Schedule the indicated files for removal from the current branch.
2424 </p>
2425 </p>
2425 <p>
2426 <p>
2426 This command schedules the files to be removed at the next commit.
2427 This command schedules the files to be removed at the next commit.
2427 To undo a remove before that, see &quot;hg revert&quot;. To undo added
2428 To undo a remove before that, see &quot;hg revert&quot;. To undo added
2428 files, see &quot;hg forget&quot;.
2429 files, see &quot;hg forget&quot;.
2429 </p>
2430 </p>
2430 <p>
2431 <p>
2431 -A/--after can be used to remove only files that have already
2432 -A/--after can be used to remove only files that have already
2432 been deleted, -f/--force can be used to force deletion, and -Af
2433 been deleted, -f/--force can be used to force deletion, and -Af
2433 can be used to remove files from the next revision without
2434 can be used to remove files from the next revision without
2434 deleting them from the working directory.
2435 deleting them from the working directory.
2435 </p>
2436 </p>
2436 <p>
2437 <p>
2437 The following table details the behavior of remove for different
2438 The following table details the behavior of remove for different
2438 file states (columns) and option combinations (rows). The file
2439 file states (columns) and option combinations (rows). The file
2439 states are Added [A], Clean [C], Modified [M] and Missing [!]
2440 states are Added [A], Clean [C], Modified [M] and Missing [!]
2440 (as reported by &quot;hg status&quot;). The actions are Warn, Remove
2441 (as reported by &quot;hg status&quot;). The actions are Warn, Remove
2441 (from branch) and Delete (from disk):
2442 (from branch) and Delete (from disk):
2442 </p>
2443 </p>
2443 <table>
2444 <table>
2444 <tr><td>opt/state</td>
2445 <tr><td>opt/state</td>
2445 <td>A</td>
2446 <td>A</td>
2446 <td>C</td>
2447 <td>C</td>
2447 <td>M</td>
2448 <td>M</td>
2448 <td>!</td></tr>
2449 <td>!</td></tr>
2449 <tr><td>none</td>
2450 <tr><td>none</td>
2450 <td>W</td>
2451 <td>W</td>
2451 <td>RD</td>
2452 <td>RD</td>
2452 <td>W</td>
2453 <td>W</td>
2453 <td>R</td></tr>
2454 <td>R</td></tr>
2454 <tr><td>-f</td>
2455 <tr><td>-f</td>
2455 <td>R</td>
2456 <td>R</td>
2456 <td>RD</td>
2457 <td>RD</td>
2457 <td>RD</td>
2458 <td>RD</td>
2458 <td>R</td></tr>
2459 <td>R</td></tr>
2459 <tr><td>-A</td>
2460 <tr><td>-A</td>
2460 <td>W</td>
2461 <td>W</td>
2461 <td>W</td>
2462 <td>W</td>
2462 <td>W</td>
2463 <td>W</td>
2463 <td>R</td></tr>
2464 <td>R</td></tr>
2464 <tr><td>-Af</td>
2465 <tr><td>-Af</td>
2465 <td>R</td>
2466 <td>R</td>
2466 <td>R</td>
2467 <td>R</td>
2467 <td>R</td>
2468 <td>R</td>
2468 <td>R</td></tr>
2469 <td>R</td></tr>
2469 </table>
2470 </table>
2470 <p>
2471 <p>
2471 <b>Note:</b>
2472 <b>Note:</b>
2472 </p>
2473 </p>
2473 <p>
2474 <p>
2474 &quot;hg remove&quot; never deletes files in Added [A] state from the
2475 &quot;hg remove&quot; never deletes files in Added [A] state from the
2475 working directory, not even if &quot;--force&quot; is specified.
2476 working directory, not even if &quot;--force&quot; is specified.
2476 </p>
2477 </p>
2477 <p>
2478 <p>
2478 Returns 0 on success, 1 if any warnings encountered.
2479 Returns 0 on success, 1 if any warnings encountered.
2479 </p>
2480 </p>
2480 <p>
2481 <p>
2481 options ([+] can be repeated):
2482 options ([+] can be repeated):
2482 </p>
2483 </p>
2483 <table>
2484 <table>
2484 <tr><td>-A</td>
2485 <tr><td>-A</td>
2485 <td>--after</td>
2486 <td>--after</td>
2486 <td>record delete for missing files</td></tr>
2487 <td>record delete for missing files</td></tr>
2487 <tr><td>-f</td>
2488 <tr><td>-f</td>
2488 <td>--force</td>
2489 <td>--force</td>
2489 <td>remove (and delete) file even if added or modified</td></tr>
2490 <td>remove (and delete) file even if added or modified</td></tr>
2490 <tr><td>-S</td>
2491 <tr><td>-S</td>
2491 <td>--subrepos</td>
2492 <td>--subrepos</td>
2492 <td>recurse into subrepositories</td></tr>
2493 <td>recurse into subrepositories</td></tr>
2493 <tr><td>-I</td>
2494 <tr><td>-I</td>
2494 <td>--include PATTERN [+]</td>
2495 <td>--include PATTERN [+]</td>
2495 <td>include names matching the given patterns</td></tr>
2496 <td>include names matching the given patterns</td></tr>
2496 <tr><td>-X</td>
2497 <tr><td>-X</td>
2497 <td>--exclude PATTERN [+]</td>
2498 <td>--exclude PATTERN [+]</td>
2498 <td>exclude names matching the given patterns</td></tr>
2499 <td>exclude names matching the given patterns</td></tr>
2499 </table>
2500 </table>
2500 <p>
2501 <p>
2501 global options ([+] can be repeated):
2502 global options ([+] can be repeated):
2502 </p>
2503 </p>
2503 <table>
2504 <table>
2504 <tr><td>-R</td>
2505 <tr><td>-R</td>
2505 <td>--repository REPO</td>
2506 <td>--repository REPO</td>
2506 <td>repository root directory or name of overlay bundle file</td></tr>
2507 <td>repository root directory or name of overlay bundle file</td></tr>
2507 <tr><td></td>
2508 <tr><td></td>
2508 <td>--cwd DIR</td>
2509 <td>--cwd DIR</td>
2509 <td>change working directory</td></tr>
2510 <td>change working directory</td></tr>
2510 <tr><td>-y</td>
2511 <tr><td>-y</td>
2511 <td>--noninteractive</td>
2512 <td>--noninteractive</td>
2512 <td>do not prompt, automatically pick the first choice for all prompts</td></tr>
2513 <td>do not prompt, automatically pick the first choice for all prompts</td></tr>
2513 <tr><td>-q</td>
2514 <tr><td>-q</td>
2514 <td>--quiet</td>
2515 <td>--quiet</td>
2515 <td>suppress output</td></tr>
2516 <td>suppress output</td></tr>
2516 <tr><td>-v</td>
2517 <tr><td>-v</td>
2517 <td>--verbose</td>
2518 <td>--verbose</td>
2518 <td>enable additional output</td></tr>
2519 <td>enable additional output</td></tr>
2519 <tr><td></td>
2520 <tr><td></td>
2520 <td>--config CONFIG [+]</td>
2521 <td>--config CONFIG [+]</td>
2521 <td>set/override config option (use 'section.name=value')</td></tr>
2522 <td>set/override config option (use 'section.name=value')</td></tr>
2522 <tr><td></td>
2523 <tr><td></td>
2523 <td>--debug</td>
2524 <td>--debug</td>
2524 <td>enable debugging output</td></tr>
2525 <td>enable debugging output</td></tr>
2525 <tr><td></td>
2526 <tr><td></td>
2526 <td>--debugger</td>
2527 <td>--debugger</td>
2527 <td>start debugger</td></tr>
2528 <td>start debugger</td></tr>
2528 <tr><td></td>
2529 <tr><td></td>
2529 <td>--encoding ENCODE</td>
2530 <td>--encoding ENCODE</td>
2530 <td>set the charset encoding (default: ascii)</td></tr>
2531 <td>set the charset encoding (default: ascii)</td></tr>
2531 <tr><td></td>
2532 <tr><td></td>
2532 <td>--encodingmode MODE</td>
2533 <td>--encodingmode MODE</td>
2533 <td>set the charset encoding mode (default: strict)</td></tr>
2534 <td>set the charset encoding mode (default: strict)</td></tr>
2534 <tr><td></td>
2535 <tr><td></td>
2535 <td>--traceback</td>
2536 <td>--traceback</td>
2536 <td>always print a traceback on exception</td></tr>
2537 <td>always print a traceback on exception</td></tr>
2537 <tr><td></td>
2538 <tr><td></td>
2538 <td>--time</td>
2539 <td>--time</td>
2539 <td>time how long the command takes</td></tr>
2540 <td>time how long the command takes</td></tr>
2540 <tr><td></td>
2541 <tr><td></td>
2541 <td>--profile</td>
2542 <td>--profile</td>
2542 <td>print command execution profile</td></tr>
2543 <td>print command execution profile</td></tr>
2543 <tr><td></td>
2544 <tr><td></td>
2544 <td>--version</td>
2545 <td>--version</td>
2545 <td>output version information and exit</td></tr>
2546 <td>output version information and exit</td></tr>
2546 <tr><td>-h</td>
2547 <tr><td>-h</td>
2547 <td>--help</td>
2548 <td>--help</td>
2548 <td>display help and exit</td></tr>
2549 <td>display help and exit</td></tr>
2549 <tr><td></td>
2550 <tr><td></td>
2550 <td>--hidden</td>
2551 <td>--hidden</td>
2551 <td>consider hidden changesets</td></tr>
2552 <td>consider hidden changesets</td></tr>
2552 </table>
2553 </table>
2553
2554
2554 </div>
2555 </div>
2555 </div>
2556 </div>
2556 </div>
2557 </div>
2557
2558
2558 <script type="text/javascript">process_dates()</script>
2559 <script type="text/javascript">process_dates()</script>
2559
2560
2560
2561
2561 </body>
2562 </body>
2562 </html>
2563 </html>
2563
2564
2564
2565
2565 $ get-with-headers.py 127.0.0.1:$HGPORT "help/revisions"
2566 $ get-with-headers.py 127.0.0.1:$HGPORT "help/revisions"
2566 200 Script output follows
2567 200 Script output follows
2567
2568
2568 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2569 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2569 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2570 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2570 <head>
2571 <head>
2571 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2572 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2572 <meta name="robots" content="index, nofollow" />
2573 <meta name="robots" content="index, nofollow" />
2573 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2574 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2574 <script type="text/javascript" src="/static/mercurial.js"></script>
2575 <script type="text/javascript" src="/static/mercurial.js"></script>
2575
2576
2576 <title>Help: revisions</title>
2577 <title>Help: revisions</title>
2577 </head>
2578 </head>
2578 <body>
2579 <body>
2579
2580
2580 <div class="container">
2581 <div class="container">
2581 <div class="menu">
2582 <div class="menu">
2582 <div class="logo">
2583 <div class="logo">
2583 <a href="https://mercurial-scm.org/">
2584 <a href="https://mercurial-scm.org/">
2584 <img src="/static/hglogo.png" alt="mercurial" /></a>
2585 <img src="/static/hglogo.png" alt="mercurial" /></a>
2585 </div>
2586 </div>
2586 <ul>
2587 <ul>
2587 <li><a href="/shortlog">log</a></li>
2588 <li><a href="/shortlog">log</a></li>
2588 <li><a href="/graph">graph</a></li>
2589 <li><a href="/graph">graph</a></li>
2589 <li><a href="/tags">tags</a></li>
2590 <li><a href="/tags">tags</a></li>
2590 <li><a href="/bookmarks">bookmarks</a></li>
2591 <li><a href="/bookmarks">bookmarks</a></li>
2591 <li><a href="/branches">branches</a></li>
2592 <li><a href="/branches">branches</a></li>
2592 </ul>
2593 </ul>
2593 <ul>
2594 <ul>
2594 <li class="active"><a href="/help">help</a></li>
2595 <li class="active"><a href="/help">help</a></li>
2595 </ul>
2596 </ul>
2596 </div>
2597 </div>
2597
2598
2598 <div class="main">
2599 <div class="main">
2599 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2600 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2600 <h3>Help: revisions</h3>
2601 <h3>Help: revisions</h3>
2601
2602
2602 <form class="search" action="/log">
2603 <form class="search" action="/log">
2603
2604
2604 <p><input name="rev" id="search1" type="text" size="30" /></p>
2605 <p><input name="rev" id="search1" type="text" size="30" /></p>
2605 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2606 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2606 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2607 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2607 </form>
2608 </form>
2608 <div id="doc">
2609 <div id="doc">
2609 <h1>Specifying Single Revisions</h1>
2610 <h1>Specifying Single Revisions</h1>
2610 <p>
2611 <p>
2611 Mercurial supports several ways to specify individual revisions.
2612 Mercurial supports several ways to specify individual revisions.
2612 </p>
2613 </p>
2613 <p>
2614 <p>
2614 A plain integer is treated as a revision number. Negative integers are
2615 A plain integer is treated as a revision number. Negative integers are
2615 treated as sequential offsets from the tip, with -1 denoting the tip,
2616 treated as sequential offsets from the tip, with -1 denoting the tip,
2616 -2 denoting the revision prior to the tip, and so forth.
2617 -2 denoting the revision prior to the tip, and so forth.
2617 </p>
2618 </p>
2618 <p>
2619 <p>
2619 A 40-digit hexadecimal string is treated as a unique revision
2620 A 40-digit hexadecimal string is treated as a unique revision
2620 identifier.
2621 identifier.
2621 </p>
2622 </p>
2622 <p>
2623 <p>
2623 A hexadecimal string less than 40 characters long is treated as a
2624 A hexadecimal string less than 40 characters long is treated as a
2624 unique revision identifier and is referred to as a short-form
2625 unique revision identifier and is referred to as a short-form
2625 identifier. A short-form identifier is only valid if it is the prefix
2626 identifier. A short-form identifier is only valid if it is the prefix
2626 of exactly one full-length identifier.
2627 of exactly one full-length identifier.
2627 </p>
2628 </p>
2628 <p>
2629 <p>
2629 Any other string is treated as a bookmark, tag, or branch name. A
2630 Any other string is treated as a bookmark, tag, or branch name. A
2630 bookmark is a movable pointer to a revision. A tag is a permanent name
2631 bookmark is a movable pointer to a revision. A tag is a permanent name
2631 associated with a revision. A branch name denotes the tipmost open branch head
2632 associated with a revision. A branch name denotes the tipmost open branch head
2632 of that branch - or if they are all closed, the tipmost closed head of the
2633 of that branch - or if they are all closed, the tipmost closed head of the
2633 branch. Bookmark, tag, and branch names must not contain the &quot;:&quot; character.
2634 branch. Bookmark, tag, and branch names must not contain the &quot;:&quot; character.
2634 </p>
2635 </p>
2635 <p>
2636 <p>
2636 The reserved name &quot;tip&quot; always identifies the most recent revision.
2637 The reserved name &quot;tip&quot; always identifies the most recent revision.
2637 </p>
2638 </p>
2638 <p>
2639 <p>
2639 The reserved name &quot;null&quot; indicates the null revision. This is the
2640 The reserved name &quot;null&quot; indicates the null revision. This is the
2640 revision of an empty repository, and the parent of revision 0.
2641 revision of an empty repository, and the parent of revision 0.
2641 </p>
2642 </p>
2642 <p>
2643 <p>
2643 The reserved name &quot;.&quot; indicates the working directory parent. If no
2644 The reserved name &quot;.&quot; indicates the working directory parent. If no
2644 working directory is checked out, it is equivalent to null. If an
2645 working directory is checked out, it is equivalent to null. If an
2645 uncommitted merge is in progress, &quot;.&quot; is the revision of the first
2646 uncommitted merge is in progress, &quot;.&quot; is the revision of the first
2646 parent.
2647 parent.
2647 </p>
2648 </p>
2648
2649
2649 </div>
2650 </div>
2650 </div>
2651 </div>
2651 </div>
2652 </div>
2652
2653
2653 <script type="text/javascript">process_dates()</script>
2654 <script type="text/javascript">process_dates()</script>
2654
2655
2655
2656
2656 </body>
2657 </body>
2657 </html>
2658 </html>
2658
2659
2659
2660
2660 Sub-topic indexes rendered properly
2661 Sub-topic indexes rendered properly
2661
2662
2662 $ get-with-headers.py 127.0.0.1:$HGPORT "help/internals"
2663 $ get-with-headers.py 127.0.0.1:$HGPORT "help/internals"
2663 200 Script output follows
2664 200 Script output follows
2664
2665
2665 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2666 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2666 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2667 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2667 <head>
2668 <head>
2668 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2669 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2669 <meta name="robots" content="index, nofollow" />
2670 <meta name="robots" content="index, nofollow" />
2670 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2671 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2671 <script type="text/javascript" src="/static/mercurial.js"></script>
2672 <script type="text/javascript" src="/static/mercurial.js"></script>
2672
2673
2673 <title>Help: internals</title>
2674 <title>Help: internals</title>
2674 </head>
2675 </head>
2675 <body>
2676 <body>
2676
2677
2677 <div class="container">
2678 <div class="container">
2678 <div class="menu">
2679 <div class="menu">
2679 <div class="logo">
2680 <div class="logo">
2680 <a href="https://mercurial-scm.org/">
2681 <a href="https://mercurial-scm.org/">
2681 <img src="/static/hglogo.png" alt="mercurial" /></a>
2682 <img src="/static/hglogo.png" alt="mercurial" /></a>
2682 </div>
2683 </div>
2683 <ul>
2684 <ul>
2684 <li><a href="/shortlog">log</a></li>
2685 <li><a href="/shortlog">log</a></li>
2685 <li><a href="/graph">graph</a></li>
2686 <li><a href="/graph">graph</a></li>
2686 <li><a href="/tags">tags</a></li>
2687 <li><a href="/tags">tags</a></li>
2687 <li><a href="/bookmarks">bookmarks</a></li>
2688 <li><a href="/bookmarks">bookmarks</a></li>
2688 <li><a href="/branches">branches</a></li>
2689 <li><a href="/branches">branches</a></li>
2689 </ul>
2690 </ul>
2690 <ul>
2691 <ul>
2691 <li><a href="/help">help</a></li>
2692 <li><a href="/help">help</a></li>
2692 </ul>
2693 </ul>
2693 </div>
2694 </div>
2694
2695
2695 <div class="main">
2696 <div class="main">
2696 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2697 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2697 <form class="search" action="/log">
2698 <form class="search" action="/log">
2698
2699
2699 <p><input name="rev" id="search1" type="text" size="30" /></p>
2700 <p><input name="rev" id="search1" type="text" size="30" /></p>
2700 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2701 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2701 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2702 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2702 </form>
2703 </form>
2703 <table class="bigtable">
2704 <table class="bigtable">
2704 <tr><td colspan="2"><h2><a name="main" href="#topics">Topics</a></h2></td></tr>
2705 <tr><td colspan="2"><h2><a name="main" href="#topics">Topics</a></h2></td></tr>
2705
2706
2706 <tr><td>
2707 <tr><td>
2707 <a href="/help/internals.bundles">
2708 <a href="/help/internals.bundles">
2708 bundles
2709 bundles
2709 </a>
2710 </a>
2710 </td><td>
2711 </td><td>
2711 container for exchange of repository data
2712 container for exchange of repository data
2712 </td></tr>
2713 </td></tr>
2713 <tr><td>
2714 <tr><td>
2714 <a href="/help/internals.changegroups">
2715 <a href="/help/internals.changegroups">
2715 changegroups
2716 changegroups
2716 </a>
2717 </a>
2717 </td><td>
2718 </td><td>
2718 representation of revlog data
2719 representation of revlog data
2719 </td></tr>
2720 </td></tr>
2720 <tr><td>
2721 <tr><td>
2721 <a href="/help/internals.revlogs">
2722 <a href="/help/internals.revlogs">
2722 revlogs
2723 revlogs
2723 </a>
2724 </a>
2724 </td><td>
2725 </td><td>
2725 revision storage mechanism
2726 revision storage mechanism
2726 </td></tr>
2727 </td></tr>
2727
2728
2728
2729
2729
2730
2730
2731
2731
2732
2732 </table>
2733 </table>
2733 </div>
2734 </div>
2734 </div>
2735 </div>
2735
2736
2736 <script type="text/javascript">process_dates()</script>
2737 <script type="text/javascript">process_dates()</script>
2737
2738
2738
2739
2739 </body>
2740 </body>
2740 </html>
2741 </html>
2741
2742
2742
2743
2743 Sub-topic topics rendered properly
2744 Sub-topic topics rendered properly
2744
2745
2745 $ get-with-headers.py 127.0.0.1:$HGPORT "help/internals.changegroups"
2746 $ get-with-headers.py 127.0.0.1:$HGPORT "help/internals.changegroups"
2746 200 Script output follows
2747 200 Script output follows
2747
2748
2748 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2749 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
2749 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2750 <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US">
2750 <head>
2751 <head>
2751 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2752 <link rel="icon" href="/static/hgicon.png" type="image/png" />
2752 <meta name="robots" content="index, nofollow" />
2753 <meta name="robots" content="index, nofollow" />
2753 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2754 <link rel="stylesheet" href="/static/style-paper.css" type="text/css" />
2754 <script type="text/javascript" src="/static/mercurial.js"></script>
2755 <script type="text/javascript" src="/static/mercurial.js"></script>
2755
2756
2756 <title>Help: internals.changegroups</title>
2757 <title>Help: internals.changegroups</title>
2757 </head>
2758 </head>
2758 <body>
2759 <body>
2759
2760
2760 <div class="container">
2761 <div class="container">
2761 <div class="menu">
2762 <div class="menu">
2762 <div class="logo">
2763 <div class="logo">
2763 <a href="https://mercurial-scm.org/">
2764 <a href="https://mercurial-scm.org/">
2764 <img src="/static/hglogo.png" alt="mercurial" /></a>
2765 <img src="/static/hglogo.png" alt="mercurial" /></a>
2765 </div>
2766 </div>
2766 <ul>
2767 <ul>
2767 <li><a href="/shortlog">log</a></li>
2768 <li><a href="/shortlog">log</a></li>
2768 <li><a href="/graph">graph</a></li>
2769 <li><a href="/graph">graph</a></li>
2769 <li><a href="/tags">tags</a></li>
2770 <li><a href="/tags">tags</a></li>
2770 <li><a href="/bookmarks">bookmarks</a></li>
2771 <li><a href="/bookmarks">bookmarks</a></li>
2771 <li><a href="/branches">branches</a></li>
2772 <li><a href="/branches">branches</a></li>
2772 </ul>
2773 </ul>
2773 <ul>
2774 <ul>
2774 <li class="active"><a href="/help">help</a></li>
2775 <li class="active"><a href="/help">help</a></li>
2775 </ul>
2776 </ul>
2776 </div>
2777 </div>
2777
2778
2778 <div class="main">
2779 <div class="main">
2779 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2780 <h2 class="breadcrumb"><a href="/">Mercurial</a> </h2>
2780 <h3>Help: internals.changegroups</h3>
2781 <h3>Help: internals.changegroups</h3>
2781
2782
2782 <form class="search" action="/log">
2783 <form class="search" action="/log">
2783
2784
2784 <p><input name="rev" id="search1" type="text" size="30" /></p>
2785 <p><input name="rev" id="search1" type="text" size="30" /></p>
2785 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2786 <div id="hint">Find changesets by keywords (author, files, the commit message), revision
2786 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2787 number or hash, or <a href="/help/revsets">revset expression</a>.</div>
2787 </form>
2788 </form>
2788 <div id="doc">
2789 <div id="doc">
2789 <h1>representation of revlog data</h1>
2790 <h1>representation of revlog data</h1>
2790 <h2>Changegroups</h2>
2791 <h2>Changegroups</h2>
2791 <p>
2792 <p>
2792 Changegroups are representations of repository revlog data, specifically
2793 Changegroups are representations of repository revlog data, specifically
2793 the changelog, manifest, and filelogs.
2794 the changelog, manifest, and filelogs.
2794 </p>
2795 </p>
2795 <p>
2796 <p>
2796 There are 3 versions of changegroups: &quot;1&quot;, &quot;2&quot;, and &quot;3&quot;. From a
2797 There are 3 versions of changegroups: &quot;1&quot;, &quot;2&quot;, and &quot;3&quot;. From a
2797 high-level, versions &quot;1&quot; and &quot;2&quot; are almost exactly the same, with
2798 high-level, versions &quot;1&quot; and &quot;2&quot; are almost exactly the same, with
2798 the only difference being a header on entries in the changeset
2799 the only difference being a header on entries in the changeset
2799 segment. Version &quot;3&quot; adds support for exchanging treemanifests and
2800 segment. Version &quot;3&quot; adds support for exchanging treemanifests and
2800 includes revlog flags in the delta header.
2801 includes revlog flags in the delta header.
2801 </p>
2802 </p>
2802 <p>
2803 <p>
2803 Changegroups consists of 3 logical segments:
2804 Changegroups consists of 3 logical segments:
2804 </p>
2805 </p>
2805 <pre>
2806 <pre>
2806 +---------------------------------+
2807 +---------------------------------+
2807 | | | |
2808 | | | |
2808 | changeset | manifest | filelogs |
2809 | changeset | manifest | filelogs |
2809 | | | |
2810 | | | |
2810 +---------------------------------+
2811 +---------------------------------+
2811 </pre>
2812 </pre>
2812 <p>
2813 <p>
2813 The principle building block of each segment is a *chunk*. A *chunk*
2814 The principle building block of each segment is a *chunk*. A *chunk*
2814 is a framed piece of data:
2815 is a framed piece of data:
2815 </p>
2816 </p>
2816 <pre>
2817 <pre>
2817 +---------------------------------------+
2818 +---------------------------------------+
2818 | | |
2819 | | |
2819 | length | data |
2820 | length | data |
2820 | (32 bits) | &lt;length&gt; bytes |
2821 | (32 bits) | &lt;length&gt; bytes |
2821 | | |
2822 | | |
2822 +---------------------------------------+
2823 +---------------------------------------+
2823 </pre>
2824 </pre>
2824 <p>
2825 <p>
2825 Each chunk starts with a 32-bit big-endian signed integer indicating
2826 Each chunk starts with a 32-bit big-endian signed integer indicating
2826 the length of the raw data that follows.
2827 the length of the raw data that follows.
2827 </p>
2828 </p>
2828 <p>
2829 <p>
2829 There is a special case chunk that has 0 length (&quot;0x00000000&quot;). We
2830 There is a special case chunk that has 0 length (&quot;0x00000000&quot;). We
2830 call this an *empty chunk*.
2831 call this an *empty chunk*.
2831 </p>
2832 </p>
2832 <h3>Delta Groups</h3>
2833 <h3>Delta Groups</h3>
2833 <p>
2834 <p>
2834 A *delta group* expresses the content of a revlog as a series of deltas,
2835 A *delta group* expresses the content of a revlog as a series of deltas,
2835 or patches against previous revisions.
2836 or patches against previous revisions.
2836 </p>
2837 </p>
2837 <p>
2838 <p>
2838 Delta groups consist of 0 or more *chunks* followed by the *empty chunk*
2839 Delta groups consist of 0 or more *chunks* followed by the *empty chunk*
2839 to signal the end of the delta group:
2840 to signal the end of the delta group:
2840 </p>
2841 </p>
2841 <pre>
2842 <pre>
2842 +------------------------------------------------------------------------+
2843 +------------------------------------------------------------------------+
2843 | | | | | |
2844 | | | | | |
2844 | chunk0 length | chunk0 data | chunk1 length | chunk1 data | 0x0 |
2845 | chunk0 length | chunk0 data | chunk1 length | chunk1 data | 0x0 |
2845 | (32 bits) | (various) | (32 bits) | (various) | (32 bits) |
2846 | (32 bits) | (various) | (32 bits) | (various) | (32 bits) |
2846 | | | | | |
2847 | | | | | |
2847 +------------------------------------------------------------+-----------+
2848 +------------------------------------------------------------+-----------+
2848 </pre>
2849 </pre>
2849 <p>
2850 <p>
2850 Each *chunk*'s data consists of the following:
2851 Each *chunk*'s data consists of the following:
2851 </p>
2852 </p>
2852 <pre>
2853 <pre>
2853 +-----------------------------------------+
2854 +-----------------------------------------+
2854 | | | |
2855 | | | |
2855 | delta header | mdiff header | delta |
2856 | delta header | mdiff header | delta |
2856 | (various) | (12 bytes) | (various) |
2857 | (various) | (12 bytes) | (various) |
2857 | | | |
2858 | | | |
2858 +-----------------------------------------+
2859 +-----------------------------------------+
2859 </pre>
2860 </pre>
2860 <p>
2861 <p>
2861 The *length* field is the byte length of the remaining 3 logical pieces
2862 The *length* field is the byte length of the remaining 3 logical pieces
2862 of data. The *delta* is a diff from an existing entry in the changelog.
2863 of data. The *delta* is a diff from an existing entry in the changelog.
2863 </p>
2864 </p>
2864 <p>
2865 <p>
2865 The *delta header* is different between versions &quot;1&quot;, &quot;2&quot;, and
2866 The *delta header* is different between versions &quot;1&quot;, &quot;2&quot;, and
2866 &quot;3&quot; of the changegroup format.
2867 &quot;3&quot; of the changegroup format.
2867 </p>
2868 </p>
2868 <p>
2869 <p>
2869 Version 1:
2870 Version 1:
2870 </p>
2871 </p>
2871 <pre>
2872 <pre>
2872 +------------------------------------------------------+
2873 +------------------------------------------------------+
2873 | | | | |
2874 | | | | |
2874 | node | p1 node | p2 node | link node |
2875 | node | p1 node | p2 node | link node |
2875 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
2876 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
2876 | | | | |
2877 | | | | |
2877 +------------------------------------------------------+
2878 +------------------------------------------------------+
2878 </pre>
2879 </pre>
2879 <p>
2880 <p>
2880 Version 2:
2881 Version 2:
2881 </p>
2882 </p>
2882 <pre>
2883 <pre>
2883 +------------------------------------------------------------------+
2884 +------------------------------------------------------------------+
2884 | | | | | |
2885 | | | | | |
2885 | node | p1 node | p2 node | base node | link node |
2886 | node | p1 node | p2 node | base node | link node |
2886 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
2887 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) |
2887 | | | | | |
2888 | | | | | |
2888 +------------------------------------------------------------------+
2889 +------------------------------------------------------------------+
2889 </pre>
2890 </pre>
2890 <p>
2891 <p>
2891 Version 3:
2892 Version 3:
2892 </p>
2893 </p>
2893 <pre>
2894 <pre>
2894 +------------------------------------------------------------------------------+
2895 +------------------------------------------------------------------------------+
2895 | | | | | | |
2896 | | | | | | |
2896 | node | p1 node | p2 node | base node | link node | flags |
2897 | node | p1 node | p2 node | base node | link node | flags |
2897 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (2 bytes) |
2898 | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (20 bytes) | (2 bytes) |
2898 | | | | | | |
2899 | | | | | | |
2899 +------------------------------------------------------------------------------+
2900 +------------------------------------------------------------------------------+
2900 </pre>
2901 </pre>
2901 <p>
2902 <p>
2902 The *mdiff header* consists of 3 32-bit big-endian signed integers
2903 The *mdiff header* consists of 3 32-bit big-endian signed integers
2903 describing offsets at which to apply the following delta content:
2904 describing offsets at which to apply the following delta content:
2904 </p>
2905 </p>
2905 <pre>
2906 <pre>
2906 +-------------------------------------+
2907 +-------------------------------------+
2907 | | | |
2908 | | | |
2908 | offset | old length | new length |
2909 | offset | old length | new length |
2909 | (32 bits) | (32 bits) | (32 bits) |
2910 | (32 bits) | (32 bits) | (32 bits) |
2910 | | | |
2911 | | | |
2911 +-------------------------------------+
2912 +-------------------------------------+
2912 </pre>
2913 </pre>
2913 <p>
2914 <p>
2914 In version 1, the delta is always applied against the previous node from
2915 In version 1, the delta is always applied against the previous node from
2915 the changegroup or the first parent if this is the first entry in the
2916 the changegroup or the first parent if this is the first entry in the
2916 changegroup.
2917 changegroup.
2917 </p>
2918 </p>
2918 <p>
2919 <p>
2919 In version 2, the delta base node is encoded in the entry in the
2920 In version 2, the delta base node is encoded in the entry in the
2920 changegroup. This allows the delta to be expressed against any parent,
2921 changegroup. This allows the delta to be expressed against any parent,
2921 which can result in smaller deltas and more efficient encoding of data.
2922 which can result in smaller deltas and more efficient encoding of data.
2922 </p>
2923 </p>
2923 <h3>Changeset Segment</h3>
2924 <h3>Changeset Segment</h3>
2924 <p>
2925 <p>
2925 The *changeset segment* consists of a single *delta group* holding
2926 The *changeset segment* consists of a single *delta group* holding
2926 changelog data. It is followed by an *empty chunk* to denote the
2927 changelog data. It is followed by an *empty chunk* to denote the
2927 boundary to the *manifests segment*.
2928 boundary to the *manifests segment*.
2928 </p>
2929 </p>
2929 <h3>Manifest Segment</h3>
2930 <h3>Manifest Segment</h3>
2930 <p>
2931 <p>
2931 The *manifest segment* consists of a single *delta group* holding
2932 The *manifest segment* consists of a single *delta group* holding
2932 manifest data. It is followed by an *empty chunk* to denote the boundary
2933 manifest data. It is followed by an *empty chunk* to denote the boundary
2933 to the *filelogs segment*.
2934 to the *filelogs segment*.
2934 </p>
2935 </p>
2935 <h3>Filelogs Segment</h3>
2936 <h3>Filelogs Segment</h3>
2936 <p>
2937 <p>
2937 The *filelogs* segment consists of multiple sub-segments, each
2938 The *filelogs* segment consists of multiple sub-segments, each
2938 corresponding to an individual file whose data is being described:
2939 corresponding to an individual file whose data is being described:
2939 </p>
2940 </p>
2940 <pre>
2941 <pre>
2941 +--------------------------------------+
2942 +--------------------------------------+
2942 | | | | |
2943 | | | | |
2943 | filelog0 | filelog1 | filelog2 | ... |
2944 | filelog0 | filelog1 | filelog2 | ... |
2944 | | | | |
2945 | | | | |
2945 +--------------------------------------+
2946 +--------------------------------------+
2946 </pre>
2947 </pre>
2947 <p>
2948 <p>
2948 In version &quot;3&quot; of the changegroup format, filelogs may include
2949 In version &quot;3&quot; of the changegroup format, filelogs may include
2949 directory logs when treemanifests are in use. directory logs are
2950 directory logs when treemanifests are in use. directory logs are
2950 identified by having a trailing '/' on their filename (see below).
2951 identified by having a trailing '/' on their filename (see below).
2951 </p>
2952 </p>
2952 <p>
2953 <p>
2953 The final filelog sub-segment is followed by an *empty chunk* to denote
2954 The final filelog sub-segment is followed by an *empty chunk* to denote
2954 the end of the segment and the overall changegroup.
2955 the end of the segment and the overall changegroup.
2955 </p>
2956 </p>
2956 <p>
2957 <p>
2957 Each filelog sub-segment consists of the following:
2958 Each filelog sub-segment consists of the following:
2958 </p>
2959 </p>
2959 <pre>
2960 <pre>
2960 +------------------------------------------+
2961 +------------------------------------------+
2961 | | | |
2962 | | | |
2962 | filename size | filename | delta group |
2963 | filename size | filename | delta group |
2963 | (32 bits) | (various) | (various) |
2964 | (32 bits) | (various) | (various) |
2964 | | | |
2965 | | | |
2965 +------------------------------------------+
2966 +------------------------------------------+
2966 </pre>
2967 </pre>
2967 <p>
2968 <p>
2968 That is, a *chunk* consisting of the filename (not terminated or padded)
2969 That is, a *chunk* consisting of the filename (not terminated or padded)
2969 followed by N chunks constituting the *delta group* for this file.
2970 followed by N chunks constituting the *delta group* for this file.
2970 </p>
2971 </p>
2971
2972
2972 </div>
2973 </div>
2973 </div>
2974 </div>
2974 </div>
2975 </div>
2975
2976
2976 <script type="text/javascript">process_dates()</script>
2977 <script type="text/javascript">process_dates()</script>
2977
2978
2978
2979
2979 </body>
2980 </body>
2980 </html>
2981 </html>
2981
2982
2982
2983
2983 $ killdaemons.py
2984 $ killdaemons.py
2984
2985
2985 #endif
2986 #endif
@@ -1,276 +1,285 b''
1 $ hg init ignorerepo
1 $ hg init ignorerepo
2 $ cd ignorerepo
2 $ cd ignorerepo
3
3
4 Issue562: .hgignore requires newline at end:
4 Issue562: .hgignore requires newline at end:
5
5
6 $ touch foo
6 $ touch foo
7 $ touch bar
7 $ touch bar
8 $ touch baz
8 $ touch baz
9 $ cat > makeignore.py <<EOF
9 $ cat > makeignore.py <<EOF
10 > f = open(".hgignore", "w")
10 > f = open(".hgignore", "w")
11 > f.write("ignore\n")
11 > f.write("ignore\n")
12 > f.write("foo\n")
12 > f.write("foo\n")
13 > # No EOL here
13 > # No EOL here
14 > f.write("bar")
14 > f.write("bar")
15 > f.close()
15 > f.close()
16 > EOF
16 > EOF
17
17
18 $ python makeignore.py
18 $ python makeignore.py
19
19
20 Should display baz only:
20 Should display baz only:
21
21
22 $ hg status
22 $ hg status
23 ? baz
23 ? baz
24
24
25 $ rm foo bar baz .hgignore makeignore.py
25 $ rm foo bar baz .hgignore makeignore.py
26
26
27 $ touch a.o
27 $ touch a.o
28 $ touch a.c
28 $ touch a.c
29 $ touch syntax
29 $ touch syntax
30 $ mkdir dir
30 $ mkdir dir
31 $ touch dir/a.o
31 $ touch dir/a.o
32 $ touch dir/b.o
32 $ touch dir/b.o
33 $ touch dir/c.o
33 $ touch dir/c.o
34
34
35 $ hg add dir/a.o
35 $ hg add dir/a.o
36 $ hg commit -m 0
36 $ hg commit -m 0
37 $ hg add dir/b.o
37 $ hg add dir/b.o
38
38
39 $ hg status
39 $ hg status
40 A dir/b.o
40 A dir/b.o
41 ? a.c
41 ? a.c
42 ? a.o
42 ? a.o
43 ? dir/c.o
43 ? dir/c.o
44 ? syntax
44 ? syntax
45
45
46 $ echo "*.o" > .hgignore
46 $ echo "*.o" > .hgignore
47 $ hg status
47 $ hg status
48 abort: $TESTTMP/ignorerepo/.hgignore: invalid pattern (relre): *.o (glob)
48 abort: $TESTTMP/ignorerepo/.hgignore: invalid pattern (relre): *.o (glob)
49 [255]
49 [255]
50
50
51 $ echo ".*\.o" > .hgignore
51 $ echo ".*\.o" > .hgignore
52 $ hg status
52 $ hg status
53 A dir/b.o
53 A dir/b.o
54 ? .hgignore
54 ? .hgignore
55 ? a.c
55 ? a.c
56 ? syntax
56 ? syntax
57
57
58 Ensure that comments work:
58 Ensure that comments work:
59
59
60 $ touch 'foo#bar' 'quux#'
60 $ touch 'foo#bar' 'quux#'
61 #if no-windows
61 #if no-windows
62 $ touch 'baz\#wat'
62 $ touch 'baz\#wat'
63 #endif
63 #endif
64 $ cat <<'EOF' >> .hgignore
64 $ cat <<'EOF' >> .hgignore
65 > # full-line comment
65 > # full-line comment
66 > # whitespace-only comment line
66 > # whitespace-only comment line
67 > syntax# pattern, no whitespace, then comment
67 > syntax# pattern, no whitespace, then comment
68 > a.c # pattern, then whitespace, then comment
68 > a.c # pattern, then whitespace, then comment
69 > baz\\# # escaped comment character
69 > baz\\# # escaped comment character
70 > foo\#b # escaped comment character
70 > foo\#b # escaped comment character
71 > quux\## escaped comment character at end of name
71 > quux\## escaped comment character at end of name
72 > EOF
72 > EOF
73 $ hg status
73 $ hg status
74 A dir/b.o
74 A dir/b.o
75 ? .hgignore
75 ? .hgignore
76 $ rm 'foo#bar' 'quux#'
76 $ rm 'foo#bar' 'quux#'
77 #if no-windows
77 #if no-windows
78 $ rm 'baz\#wat'
78 $ rm 'baz\#wat'
79 #endif
79 #endif
80
80
81 Check it does not ignore the current directory '.':
81 Check it does not ignore the current directory '.':
82
82
83 $ echo "^\." > .hgignore
83 $ echo "^\." > .hgignore
84 $ hg status
84 $ hg status
85 A dir/b.o
85 A dir/b.o
86 ? a.c
86 ? a.c
87 ? a.o
87 ? a.o
88 ? dir/c.o
88 ? dir/c.o
89 ? syntax
89 ? syntax
90
90
91 Test that patterns from ui.ignore options are read:
91 Test that patterns from ui.ignore options are read:
92
92
93 $ echo > .hgignore
93 $ echo > .hgignore
94 $ cat >> $HGRCPATH << EOF
94 $ cat >> $HGRCPATH << EOF
95 > [ui]
95 > [ui]
96 > ignore.other = $TESTTMP/ignorerepo/.hg/testhgignore
96 > ignore.other = $TESTTMP/ignorerepo/.hg/testhgignore
97 > EOF
97 > EOF
98 $ echo "glob:**.o" > .hg/testhgignore
98 $ echo "glob:**.o" > .hg/testhgignore
99 $ hg status
99 $ hg status
100 A dir/b.o
100 A dir/b.o
101 ? .hgignore
101 ? .hgignore
102 ? a.c
102 ? a.c
103 ? syntax
103 ? syntax
104
104
105 empty out testhgignore
105 empty out testhgignore
106 $ echo > .hg/testhgignore
106 $ echo > .hg/testhgignore
107
107
108 Test relative ignore path (issue4473):
108 Test relative ignore path (issue4473):
109
109
110 $ cat >> $HGRCPATH << EOF
110 $ cat >> $HGRCPATH << EOF
111 > [ui]
111 > [ui]
112 > ignore.relative = .hg/testhgignorerel
112 > ignore.relative = .hg/testhgignorerel
113 > EOF
113 > EOF
114 $ echo "glob:*.o" > .hg/testhgignorerel
114 $ echo "glob:*.o" > .hg/testhgignorerel
115 $ cd dir
115 $ cd dir
116 $ hg status
116 $ hg status
117 A dir/b.o
117 A dir/b.o
118 ? .hgignore
118 ? .hgignore
119 ? a.c
119 ? a.c
120 ? syntax
120 ? syntax
121
121
122 $ cd ..
122 $ cd ..
123 $ echo > .hg/testhgignorerel
123 $ echo > .hg/testhgignorerel
124 $ echo "syntax: glob" > .hgignore
124 $ echo "syntax: glob" > .hgignore
125 $ echo "re:.*\.o" >> .hgignore
125 $ echo "re:.*\.o" >> .hgignore
126 $ hg status
126 $ hg status
127 A dir/b.o
127 A dir/b.o
128 ? .hgignore
128 ? .hgignore
129 ? a.c
129 ? a.c
130 ? syntax
130 ? syntax
131
131
132 $ echo "syntax: invalid" > .hgignore
132 $ echo "syntax: invalid" > .hgignore
133 $ hg status
133 $ hg status
134 $TESTTMP/ignorerepo/.hgignore: ignoring invalid syntax 'invalid' (glob)
134 $TESTTMP/ignorerepo/.hgignore: ignoring invalid syntax 'invalid' (glob)
135 A dir/b.o
135 A dir/b.o
136 ? .hgignore
136 ? .hgignore
137 ? a.c
137 ? a.c
138 ? a.o
138 ? a.o
139 ? dir/c.o
139 ? dir/c.o
140 ? syntax
140 ? syntax
141
141
142 $ echo "syntax: glob" > .hgignore
142 $ echo "syntax: glob" > .hgignore
143 $ echo "*.o" >> .hgignore
143 $ echo "*.o" >> .hgignore
144 $ hg status
144 $ hg status
145 A dir/b.o
145 A dir/b.o
146 ? .hgignore
146 ? .hgignore
147 ? a.c
147 ? a.c
148 ? syntax
148 ? syntax
149
149
150 $ echo "relglob:syntax*" > .hgignore
150 $ echo "relglob:syntax*" > .hgignore
151 $ hg status
151 $ hg status
152 A dir/b.o
152 A dir/b.o
153 ? .hgignore
153 ? .hgignore
154 ? a.c
154 ? a.c
155 ? a.o
155 ? a.o
156 ? dir/c.o
156 ? dir/c.o
157
157
158 $ echo "relglob:*" > .hgignore
158 $ echo "relglob:*" > .hgignore
159 $ hg status
159 $ hg status
160 A dir/b.o
160 A dir/b.o
161
161
162 $ cd dir
162 $ cd dir
163 $ hg status .
163 $ hg status .
164 A b.o
164 A b.o
165
165
166 $ hg debugignore
166 $ hg debugignore
167 (?:(?:|.*/)[^/]*(?:/|$))
167 (?:(?:|.*/)[^/]*(?:/|$))
168
168
169 $ hg debugignore b.o
170 b.o is ignored
171
169 $ cd ..
172 $ cd ..
170
173
171 Check patterns that match only the directory
174 Check patterns that match only the directory
172
175
173 $ echo "^dir\$" > .hgignore
176 $ echo "^dir\$" > .hgignore
174 $ hg status
177 $ hg status
175 A dir/b.o
178 A dir/b.o
176 ? .hgignore
179 ? .hgignore
177 ? a.c
180 ? a.c
178 ? a.o
181 ? a.o
179 ? syntax
182 ? syntax
180
183
181 Check recursive glob pattern matches no directories (dir/**/c.o matches dir/c.o)
184 Check recursive glob pattern matches no directories (dir/**/c.o matches dir/c.o)
182
185
183 $ echo "syntax: glob" > .hgignore
186 $ echo "syntax: glob" > .hgignore
184 $ echo "dir/**/c.o" >> .hgignore
187 $ echo "dir/**/c.o" >> .hgignore
185 $ touch dir/c.o
188 $ touch dir/c.o
186 $ mkdir dir/subdir
189 $ mkdir dir/subdir
187 $ touch dir/subdir/c.o
190 $ touch dir/subdir/c.o
188 $ hg status
191 $ hg status
189 A dir/b.o
192 A dir/b.o
190 ? .hgignore
193 ? .hgignore
191 ? a.c
194 ? a.c
192 ? a.o
195 ? a.o
193 ? syntax
196 ? syntax
197 $ hg debugignore a.c
198 a.c is not ignored
199 $ hg debugignore dir/c.o
200 dir/c.o is ignored
194
201
195 Check using 'include:' in ignore file
202 Check using 'include:' in ignore file
196
203
197 $ hg purge --all --config extensions.purge=
204 $ hg purge --all --config extensions.purge=
198 $ touch foo.included
205 $ touch foo.included
199
206
200 $ echo ".*.included" > otherignore
207 $ echo ".*.included" > otherignore
201 $ hg status -I "include:otherignore"
208 $ hg status -I "include:otherignore"
202 ? foo.included
209 ? foo.included
203
210
204 $ echo "include:otherignore" >> .hgignore
211 $ echo "include:otherignore" >> .hgignore
205 $ hg status
212 $ hg status
206 A dir/b.o
213 A dir/b.o
207 ? .hgignore
214 ? .hgignore
208 ? otherignore
215 ? otherignore
209
216
210 Check recursive uses of 'include:'
217 Check recursive uses of 'include:'
211
218
212 $ echo "include:nested/ignore" >> otherignore
219 $ echo "include:nested/ignore" >> otherignore
213 $ mkdir nested
220 $ mkdir nested
214 $ echo "glob:*ignore" > nested/ignore
221 $ echo "glob:*ignore" > nested/ignore
215 $ hg status
222 $ hg status
216 A dir/b.o
223 A dir/b.o
217
224
218 $ cp otherignore goodignore
225 $ cp otherignore goodignore
219 $ echo "include:badignore" >> otherignore
226 $ echo "include:badignore" >> otherignore
220 $ hg status
227 $ hg status
221 skipping unreadable pattern file 'badignore': No such file or directory
228 skipping unreadable pattern file 'badignore': No such file or directory
222 A dir/b.o
229 A dir/b.o
223
230
224 $ mv goodignore otherignore
231 $ mv goodignore otherignore
225
232
226 Check using 'include:' while in a non-root directory
233 Check using 'include:' while in a non-root directory
227
234
228 $ cd ..
235 $ cd ..
229 $ hg -R ignorerepo status
236 $ hg -R ignorerepo status
230 A dir/b.o
237 A dir/b.o
231 $ cd ignorerepo
238 $ cd ignorerepo
232
239
233 Check including subincludes
240 Check including subincludes
234
241
235 $ hg revert -q --all
242 $ hg revert -q --all
236 $ hg purge --all --config extensions.purge=
243 $ hg purge --all --config extensions.purge=
237 $ echo ".hgignore" > .hgignore
244 $ echo ".hgignore" > .hgignore
238 $ mkdir dir1 dir2
245 $ mkdir dir1 dir2
239 $ touch dir1/file1 dir1/file2 dir2/file1 dir2/file2
246 $ touch dir1/file1 dir1/file2 dir2/file1 dir2/file2
240 $ echo "subinclude:dir2/.hgignore" >> .hgignore
247 $ echo "subinclude:dir2/.hgignore" >> .hgignore
241 $ echo "glob:file*2" > dir2/.hgignore
248 $ echo "glob:file*2" > dir2/.hgignore
242 $ hg status
249 $ hg status
243 ? dir1/file1
250 ? dir1/file1
244 ? dir1/file2
251 ? dir1/file2
245 ? dir2/file1
252 ? dir2/file1
246
253
247 Check including subincludes with regexs
254 Check including subincludes with regexs
248
255
249 $ echo "subinclude:dir1/.hgignore" >> .hgignore
256 $ echo "subinclude:dir1/.hgignore" >> .hgignore
250 $ echo "regexp:f.le1" > dir1/.hgignore
257 $ echo "regexp:f.le1" > dir1/.hgignore
251
258
252 $ hg status
259 $ hg status
253 ? dir1/file2
260 ? dir1/file2
254 ? dir2/file1
261 ? dir2/file1
255
262
256 Check multiple levels of sub-ignores
263 Check multiple levels of sub-ignores
257
264
258 $ mkdir dir1/subdir
265 $ mkdir dir1/subdir
259 $ touch dir1/subdir/subfile1 dir1/subdir/subfile3 dir1/subdir/subfile4
266 $ touch dir1/subdir/subfile1 dir1/subdir/subfile3 dir1/subdir/subfile4
260 $ echo "subinclude:subdir/.hgignore" >> dir1/.hgignore
267 $ echo "subinclude:subdir/.hgignore" >> dir1/.hgignore
261 $ echo "glob:subfil*3" >> dir1/subdir/.hgignore
268 $ echo "glob:subfil*3" >> dir1/subdir/.hgignore
262
269
263 $ hg status
270 $ hg status
264 ? dir1/file2
271 ? dir1/file2
265 ? dir1/subdir/subfile4
272 ? dir1/subdir/subfile4
266 ? dir2/file1
273 ? dir2/file1
267
274
268 Check include subignore at the same level
275 Check include subignore at the same level
269
276
270 $ mv dir1/subdir/.hgignore dir1/.hgignoretwo
277 $ mv dir1/subdir/.hgignore dir1/.hgignoretwo
271 $ echo "regexp:f.le1" > dir1/.hgignore
278 $ echo "regexp:f.le1" > dir1/.hgignore
272 $ echo "subinclude:.hgignoretwo" >> dir1/.hgignore
279 $ echo "subinclude:.hgignoretwo" >> dir1/.hgignore
273 $ echo "glob:file*2" > dir1/.hgignoretwo
280 $ echo "glob:file*2" > dir1/.hgignoretwo
274
281
275 $ hg status | grep file2
282 $ hg status | grep file2
276 [1]
283 [1]
284 $ hg debugignore dir1/file2
285 dir1/file2 is ignored
General Comments 0
You need to be logged in to leave comments. Login now