##// END OF EJS Templates
record: check that we are not committing a merge before patch selection...
Nicolas Dumazet -
r11237:feb2a58f stable
parent child Browse files
Show More
@@ -1,552 +1,559
1 1 # record.py
2 2 #
3 3 # Copyright 2007 Bryan O'Sullivan <bos@serpentine.com>
4 4 #
5 5 # This software may be used and distributed according to the terms of the
6 6 # GNU General Public License version 2 or any later version.
7 7
8 8 '''commands to interactively select changes for commit/qrefresh'''
9 9
10 10 from mercurial.i18n import gettext, _
11 11 from mercurial import cmdutil, commands, extensions, hg, mdiff, patch
12 12 from mercurial import util
13 13 import copy, cStringIO, errno, operator, os, re, tempfile
14 14
15 15 lines_re = re.compile(r'@@ -(\d+),(\d+) \+(\d+),(\d+) @@\s*(.*)')
16 16
17 17 def scanpatch(fp):
18 18 """like patch.iterhunks, but yield different events
19 19
20 20 - ('file', [header_lines + fromfile + tofile])
21 21 - ('context', [context_lines])
22 22 - ('hunk', [hunk_lines])
23 23 - ('range', (-start,len, +start,len, diffp))
24 24 """
25 25 lr = patch.linereader(fp)
26 26
27 27 def scanwhile(first, p):
28 28 """scan lr while predicate holds"""
29 29 lines = [first]
30 30 while True:
31 31 line = lr.readline()
32 32 if not line:
33 33 break
34 34 if p(line):
35 35 lines.append(line)
36 36 else:
37 37 lr.push(line)
38 38 break
39 39 return lines
40 40
41 41 while True:
42 42 line = lr.readline()
43 43 if not line:
44 44 break
45 45 if line.startswith('diff --git a/'):
46 46 def notheader(line):
47 47 s = line.split(None, 1)
48 48 return not s or s[0] not in ('---', 'diff')
49 49 header = scanwhile(line, notheader)
50 50 fromfile = lr.readline()
51 51 if fromfile.startswith('---'):
52 52 tofile = lr.readline()
53 53 header += [fromfile, tofile]
54 54 else:
55 55 lr.push(fromfile)
56 56 yield 'file', header
57 57 elif line[0] == ' ':
58 58 yield 'context', scanwhile(line, lambda l: l[0] in ' \\')
59 59 elif line[0] in '-+':
60 60 yield 'hunk', scanwhile(line, lambda l: l[0] in '-+\\')
61 61 else:
62 62 m = lines_re.match(line)
63 63 if m:
64 64 yield 'range', m.groups()
65 65 else:
66 66 raise patch.PatchError('unknown patch content: %r' % line)
67 67
68 68 class header(object):
69 69 """patch header
70 70
71 71 XXX shoudn't we move this to mercurial/patch.py ?
72 72 """
73 73 diff_re = re.compile('diff --git a/(.*) b/(.*)$')
74 74 allhunks_re = re.compile('(?:index|new file|deleted file) ')
75 75 pretty_re = re.compile('(?:new file|deleted file) ')
76 76 special_re = re.compile('(?:index|new|deleted|copy|rename) ')
77 77
78 78 def __init__(self, header):
79 79 self.header = header
80 80 self.hunks = []
81 81
82 82 def binary(self):
83 83 for h in self.header:
84 84 if h.startswith('index '):
85 85 return True
86 86
87 87 def pretty(self, fp):
88 88 for h in self.header:
89 89 if h.startswith('index '):
90 90 fp.write(_('this modifies a binary file (all or nothing)\n'))
91 91 break
92 92 if self.pretty_re.match(h):
93 93 fp.write(h)
94 94 if self.binary():
95 95 fp.write(_('this is a binary file\n'))
96 96 break
97 97 if h.startswith('---'):
98 98 fp.write(_('%d hunks, %d lines changed\n') %
99 99 (len(self.hunks),
100 100 sum([h.added + h.removed for h in self.hunks])))
101 101 break
102 102 fp.write(h)
103 103
104 104 def write(self, fp):
105 105 fp.write(''.join(self.header))
106 106
107 107 def allhunks(self):
108 108 for h in self.header:
109 109 if self.allhunks_re.match(h):
110 110 return True
111 111
112 112 def files(self):
113 113 fromfile, tofile = self.diff_re.match(self.header[0]).groups()
114 114 if fromfile == tofile:
115 115 return [fromfile]
116 116 return [fromfile, tofile]
117 117
118 118 def filename(self):
119 119 return self.files()[-1]
120 120
121 121 def __repr__(self):
122 122 return '<header %s>' % (' '.join(map(repr, self.files())))
123 123
124 124 def special(self):
125 125 for h in self.header:
126 126 if self.special_re.match(h):
127 127 return True
128 128
129 129 def countchanges(hunk):
130 130 """hunk -> (n+,n-)"""
131 131 add = len([h for h in hunk if h[0] == '+'])
132 132 rem = len([h for h in hunk if h[0] == '-'])
133 133 return add, rem
134 134
135 135 class hunk(object):
136 136 """patch hunk
137 137
138 138 XXX shouldn't we merge this with patch.hunk ?
139 139 """
140 140 maxcontext = 3
141 141
142 142 def __init__(self, header, fromline, toline, proc, before, hunk, after):
143 143 def trimcontext(number, lines):
144 144 delta = len(lines) - self.maxcontext
145 145 if False and delta > 0:
146 146 return number + delta, lines[:self.maxcontext]
147 147 return number, lines
148 148
149 149 self.header = header
150 150 self.fromline, self.before = trimcontext(fromline, before)
151 151 self.toline, self.after = trimcontext(toline, after)
152 152 self.proc = proc
153 153 self.hunk = hunk
154 154 self.added, self.removed = countchanges(self.hunk)
155 155
156 156 def write(self, fp):
157 157 delta = len(self.before) + len(self.after)
158 158 if self.after and self.after[-1] == '\\ No newline at end of file\n':
159 159 delta -= 1
160 160 fromlen = delta + self.removed
161 161 tolen = delta + self.added
162 162 fp.write('@@ -%d,%d +%d,%d @@%s\n' %
163 163 (self.fromline, fromlen, self.toline, tolen,
164 164 self.proc and (' ' + self.proc)))
165 165 fp.write(''.join(self.before + self.hunk + self.after))
166 166
167 167 pretty = write
168 168
169 169 def filename(self):
170 170 return self.header.filename()
171 171
172 172 def __repr__(self):
173 173 return '<hunk %r@%d>' % (self.filename(), self.fromline)
174 174
175 175 def parsepatch(fp):
176 176 """patch -> [] of hunks """
177 177 class parser(object):
178 178 """patch parsing state machine"""
179 179 def __init__(self):
180 180 self.fromline = 0
181 181 self.toline = 0
182 182 self.proc = ''
183 183 self.header = None
184 184 self.context = []
185 185 self.before = []
186 186 self.hunk = []
187 187 self.stream = []
188 188
189 189 def addrange(self, (fromstart, fromend, tostart, toend, proc)):
190 190 self.fromline = int(fromstart)
191 191 self.toline = int(tostart)
192 192 self.proc = proc
193 193
194 194 def addcontext(self, context):
195 195 if self.hunk:
196 196 h = hunk(self.header, self.fromline, self.toline, self.proc,
197 197 self.before, self.hunk, context)
198 198 self.header.hunks.append(h)
199 199 self.stream.append(h)
200 200 self.fromline += len(self.before) + h.removed
201 201 self.toline += len(self.before) + h.added
202 202 self.before = []
203 203 self.hunk = []
204 204 self.proc = ''
205 205 self.context = context
206 206
207 207 def addhunk(self, hunk):
208 208 if self.context:
209 209 self.before = self.context
210 210 self.context = []
211 211 self.hunk = hunk
212 212
213 213 def newfile(self, hdr):
214 214 self.addcontext([])
215 215 h = header(hdr)
216 216 self.stream.append(h)
217 217 self.header = h
218 218
219 219 def finished(self):
220 220 self.addcontext([])
221 221 return self.stream
222 222
223 223 transitions = {
224 224 'file': {'context': addcontext,
225 225 'file': newfile,
226 226 'hunk': addhunk,
227 227 'range': addrange},
228 228 'context': {'file': newfile,
229 229 'hunk': addhunk,
230 230 'range': addrange},
231 231 'hunk': {'context': addcontext,
232 232 'file': newfile,
233 233 'range': addrange},
234 234 'range': {'context': addcontext,
235 235 'hunk': addhunk},
236 236 }
237 237
238 238 p = parser()
239 239
240 240 state = 'context'
241 241 for newstate, data in scanpatch(fp):
242 242 try:
243 243 p.transitions[state][newstate](p, data)
244 244 except KeyError:
245 245 raise patch.PatchError('unhandled transition: %s -> %s' %
246 246 (state, newstate))
247 247 state = newstate
248 248 return p.finished()
249 249
250 250 def filterpatch(ui, chunks):
251 251 """Interactively filter patch chunks into applied-only chunks"""
252 252 chunks = list(chunks)
253 253 chunks.reverse()
254 254 seen = set()
255 255 def consumefile():
256 256 """fetch next portion from chunks until a 'header' is seen
257 257 NB: header == new-file mark
258 258 """
259 259 consumed = []
260 260 while chunks:
261 261 if isinstance(chunks[-1], header):
262 262 break
263 263 else:
264 264 consumed.append(chunks.pop())
265 265 return consumed
266 266
267 267 resp_all = [None] # this two are changed from inside prompt,
268 268 resp_file = [None] # so can't be usual variables
269 269 applied = {} # 'filename' -> [] of chunks
270 270 def prompt(query):
271 271 """prompt query, and process base inputs
272 272
273 273 - y/n for the rest of file
274 274 - y/n for the rest
275 275 - ? (help)
276 276 - q (quit)
277 277
278 278 Returns True/False and sets reps_all and resp_file as
279 279 appropriate.
280 280 """
281 281 if resp_all[0] is not None:
282 282 return resp_all[0]
283 283 if resp_file[0] is not None:
284 284 return resp_file[0]
285 285 while True:
286 286 resps = _('[Ynsfdaq?]')
287 287 choices = (_('&Yes, record this change'),
288 288 _('&No, skip this change'),
289 289 _('&Skip remaining changes to this file'),
290 290 _('Record remaining changes to this &file'),
291 291 _('&Done, skip remaining changes and files'),
292 292 _('Record &all changes to all remaining files'),
293 293 _('&Quit, recording no changes'),
294 294 _('&?'))
295 295 r = ui.promptchoice("%s %s" % (query, resps), choices)
296 296 if r == 7: # ?
297 297 doc = gettext(record.__doc__)
298 298 c = doc.find('::') + 2
299 299 for l in doc[c:].splitlines():
300 300 if l.startswith(' '):
301 301 ui.write(l.strip(), '\n')
302 302 continue
303 303 elif r == 0: # yes
304 304 ret = True
305 305 elif r == 1: # no
306 306 ret = False
307 307 elif r == 2: # Skip
308 308 ret = resp_file[0] = False
309 309 elif r == 3: # file (Record remaining)
310 310 ret = resp_file[0] = True
311 311 elif r == 4: # done, skip remaining
312 312 ret = resp_all[0] = False
313 313 elif r == 5: # all
314 314 ret = resp_all[0] = True
315 315 elif r == 6: # quit
316 316 raise util.Abort(_('user quit'))
317 317 return ret
318 318 pos, total = 0, len(chunks) - 1
319 319 while chunks:
320 320 pos = total - len(chunks) + 1
321 321 chunk = chunks.pop()
322 322 if isinstance(chunk, header):
323 323 # new-file mark
324 324 resp_file = [None]
325 325 fixoffset = 0
326 326 hdr = ''.join(chunk.header)
327 327 if hdr in seen:
328 328 consumefile()
329 329 continue
330 330 seen.add(hdr)
331 331 if resp_all[0] is None:
332 332 chunk.pretty(ui)
333 333 r = prompt(_('examine changes to %s?') %
334 334 _(' and ').join(map(repr, chunk.files())))
335 335 if r:
336 336 applied[chunk.filename()] = [chunk]
337 337 if chunk.allhunks():
338 338 applied[chunk.filename()] += consumefile()
339 339 else:
340 340 consumefile()
341 341 else:
342 342 # new hunk
343 343 if resp_file[0] is None and resp_all[0] is None:
344 344 chunk.pretty(ui)
345 345 r = total == 1 and prompt(_('record this change to %r?') %
346 346 chunk.filename()) \
347 347 or prompt(_('record change %d/%d to %r?') %
348 348 (pos, total, chunk.filename()))
349 349 if r:
350 350 if fixoffset:
351 351 chunk = copy.copy(chunk)
352 352 chunk.toline += fixoffset
353 353 applied[chunk.filename()].append(chunk)
354 354 else:
355 355 fixoffset += chunk.removed - chunk.added
356 356 return reduce(operator.add, [h for h in applied.itervalues()
357 357 if h[0].special() or len(h) > 1], [])
358 358
359 359 def record(ui, repo, *pats, **opts):
360 360 '''interactively select changes to commit
361 361
362 362 If a list of files is omitted, all changes reported by "hg status"
363 363 will be candidates for recording.
364 364
365 365 See 'hg help dates' for a list of formats valid for -d/--date.
366 366
367 367 You will be prompted for whether to record changes to each
368 368 modified file, and for files with multiple changes, for each
369 369 change to use. For each query, the following responses are
370 370 possible::
371 371
372 372 y - record this change
373 373 n - skip this change
374 374
375 375 s - skip remaining changes to this file
376 376 f - record remaining changes to this file
377 377
378 378 d - done, skip remaining changes and files
379 379 a - record all changes to all remaining files
380 380 q - quit, recording no changes
381 381
382 ? - display help'''
382 ? - display help
383
384 This command is not available when committing a merge.'''
383 385
384 386 dorecord(ui, repo, commands.commit, *pats, **opts)
385 387
386 388
387 389 def qrecord(ui, repo, patch, *pats, **opts):
388 390 '''interactively record a new patch
389 391
390 392 See 'hg help qnew' & 'hg help record' for more information and
391 393 usage.
392 394 '''
393 395
394 396 try:
395 397 mq = extensions.find('mq')
396 398 except KeyError:
397 399 raise util.Abort(_("'mq' extension not loaded"))
398 400
399 401 def committomq(ui, repo, *pats, **opts):
400 402 mq.new(ui, repo, patch, *pats, **opts)
401 403
402 404 opts = opts.copy()
403 405 opts['force'] = True # always 'qnew -f'
404 406 dorecord(ui, repo, committomq, *pats, **opts)
405 407
406 408
407 409 def dorecord(ui, repo, commitfunc, *pats, **opts):
408 410 if not ui.interactive():
409 411 raise util.Abort(_('running non-interactively, use commit instead'))
410 412
411 413 def recordfunc(ui, repo, message, match, opts):
412 414 """This is generic record driver.
413 415
414 416 Its job is to interactively filter local changes, and accordingly
415 417 prepare working dir into a state, where the job can be delegated to
416 418 non-interactive commit command such as 'commit' or 'qrefresh'.
417 419
418 420 After the actual job is done by non-interactive command, working dir
419 421 state is restored to original.
420 422
421 423 In the end we'll record interesting changes, and everything else will be
422 424 left in place, so the user can continue his work.
423 425 """
424 426
427 merge = len(repo[None].parents()) > 1
428 if merge:
429 raise util.Abort(_('cannot partially commit a merge '
430 '(use hg commit instead)'))
431
425 432 changes = repo.status(match=match)[:3]
426 433 diffopts = mdiff.diffopts(git=True, nodates=True)
427 434 chunks = patch.diff(repo, changes=changes, opts=diffopts)
428 435 fp = cStringIO.StringIO()
429 436 fp.write(''.join(chunks))
430 437 fp.seek(0)
431 438
432 439 # 1. filter patch, so we have intending-to apply subset of it
433 440 chunks = filterpatch(ui, parsepatch(fp))
434 441 del fp
435 442
436 443 contenders = set()
437 444 for h in chunks:
438 445 try:
439 446 contenders.update(set(h.files()))
440 447 except AttributeError:
441 448 pass
442 449
443 450 changed = changes[0] + changes[1] + changes[2]
444 451 newfiles = [f for f in changed if f in contenders]
445 452 if not newfiles:
446 453 ui.status(_('no changes to record\n'))
447 454 return 0
448 455
449 456 modified = set(changes[0])
450 457
451 458 # 2. backup changed files, so we can restore them in the end
452 459 backups = {}
453 460 backupdir = repo.join('record-backups')
454 461 try:
455 462 os.mkdir(backupdir)
456 463 except OSError, err:
457 464 if err.errno != errno.EEXIST:
458 465 raise
459 466 try:
460 467 # backup continues
461 468 for f in newfiles:
462 469 if f not in modified:
463 470 continue
464 471 fd, tmpname = tempfile.mkstemp(prefix=f.replace('/', '_')+'.',
465 472 dir=backupdir)
466 473 os.close(fd)
467 474 ui.debug('backup %r as %r\n' % (f, tmpname))
468 475 util.copyfile(repo.wjoin(f), tmpname)
469 476 backups[f] = tmpname
470 477
471 478 fp = cStringIO.StringIO()
472 479 for c in chunks:
473 480 if c.filename() in backups:
474 481 c.write(fp)
475 482 dopatch = fp.tell()
476 483 fp.seek(0)
477 484
478 485 # 3a. apply filtered patch to clean repo (clean)
479 486 if backups:
480 487 hg.revert(repo, repo.dirstate.parents()[0], backups.has_key)
481 488
482 489 # 3b. (apply)
483 490 if dopatch:
484 491 try:
485 492 ui.debug('applying patch\n')
486 493 ui.debug(fp.getvalue())
487 494 pfiles = {}
488 495 patch.internalpatch(fp, ui, 1, repo.root, files=pfiles,
489 496 eolmode=None)
490 497 patch.updatedir(ui, repo, pfiles)
491 498 except patch.PatchError, err:
492 499 s = str(err)
493 500 if s:
494 501 raise util.Abort(s)
495 502 else:
496 503 raise util.Abort(_('patch failed to apply'))
497 504 del fp
498 505
499 506 # 4. We prepared working directory according to filtered patch.
500 507 # Now is the time to delegate the job to commit/qrefresh or the like!
501 508
502 509 # it is important to first chdir to repo root -- we'll call a
503 510 # highlevel command with list of pathnames relative to repo root
504 511 cwd = os.getcwd()
505 512 os.chdir(repo.root)
506 513 try:
507 514 commitfunc(ui, repo, *newfiles, **opts)
508 515 finally:
509 516 os.chdir(cwd)
510 517
511 518 return 0
512 519 finally:
513 520 # 5. finally restore backed-up files
514 521 try:
515 522 for realname, tmpname in backups.iteritems():
516 523 ui.debug('restoring %r to %r\n' % (tmpname, realname))
517 524 util.copyfile(tmpname, repo.wjoin(realname))
518 525 os.unlink(tmpname)
519 526 os.rmdir(backupdir)
520 527 except OSError:
521 528 pass
522 529 return cmdutil.commit(ui, repo, recordfunc, pats, opts)
523 530
524 531 cmdtable = {
525 532 "record":
526 533 (record,
527 534
528 535 # add commit options
529 536 commands.table['^commit|ci'][1],
530 537
531 538 _('hg record [OPTION]... [FILE]...')),
532 539 }
533 540
534 541
535 542 def uisetup(ui):
536 543 try:
537 544 mq = extensions.find('mq')
538 545 except KeyError:
539 546 return
540 547
541 548 qcmdtable = {
542 549 "qrecord":
543 550 (qrecord,
544 551
545 552 # add qnew options, except '--force'
546 553 [opt for opt in mq.cmdtable['qnew'][1] if opt[1] != 'force'],
547 554
548 555 _('hg qrecord [OPTION]... PATCH [FILE]...')),
549 556 }
550 557
551 558 cmdtable.update(qcmdtable)
552 559
@@ -1,318 +1,329
1 1 #!/bin/sh
2 2
3 3 echo "[ui]" >> $HGRCPATH
4 4 echo "interactive=true" >> $HGRCPATH
5 5 echo "[extensions]" >> $HGRCPATH
6 6 echo "record=" >> $HGRCPATH
7 7
8 8 echo % help
9 9
10 10 hg help record
11 11
12 12 hg init a
13 13 cd a
14 14
15 15 echo % select no files
16 16
17 17 touch empty-rw
18 18 hg add empty-rw
19 19 hg record empty-rw<<EOF
20 20 n
21 21 EOF
22 22 echo; hg tip -p
23 23
24 24 echo % select files but no hunks
25 25
26 26 hg record empty-rw<<EOF
27 27 y
28 28 n
29 29 EOF
30 30 echo; hg tip -p
31 31
32 32 echo % record empty file
33 33
34 34 hg record -d '0 0' -m empty empty-rw<<EOF
35 35 y
36 36 y
37 37 EOF
38 38 echo; hg tip -p
39 39
40 40 echo % rename empty file
41 41
42 42 hg mv empty-rw empty-rename
43 43 hg record -d '1 0' -m rename<<EOF
44 44 y
45 45 EOF
46 46 echo; hg tip -p
47 47
48 48 echo % copy empty file
49 49
50 50 hg cp empty-rename empty-copy
51 51 hg record -d '2 0' -m copy<<EOF
52 52 y
53 53 EOF
54 54 echo; hg tip -p
55 55
56 56 echo % delete empty file
57 57
58 58 hg rm empty-copy
59 59 hg record -d '3 0' -m delete<<EOF
60 60 y
61 61 EOF
62 62 echo; hg tip -p
63 63
64 64 echo % add binary file
65 65
66 66 hg bundle --base -2 tip.bundle
67 67 hg add tip.bundle
68 68 hg record -d '4 0' -m binary<<EOF
69 69 y
70 70 EOF
71 71 echo; hg tip -p
72 72
73 73 echo % change binary file
74 74
75 75 hg bundle --base -2 tip.bundle
76 76 hg record -d '5 0' -m binary-change<<EOF
77 77 y
78 78 EOF
79 79 echo; hg tip -p
80 80
81 81 echo % rename and change binary file
82 82
83 83 hg mv tip.bundle top.bundle
84 84 hg bundle --base -2 top.bundle
85 85 hg record -d '6 0' -m binary-change-rename<<EOF
86 86 y
87 87 EOF
88 88 echo; hg tip -p
89 89
90 90 echo % add plain file
91 91
92 92 for i in 1 2 3 4 5 6 7 8 9 10; do
93 93 echo $i >> plain
94 94 done
95 95
96 96 hg add plain
97 97 hg record -d '7 0' -m plain plain<<EOF
98 98 y
99 99 y
100 100 EOF
101 101 echo; hg tip -p
102 102
103 103 echo % modify end of plain file
104 104
105 105 echo 11 >> plain
106 106 hg record -d '8 0' -m end plain <<EOF
107 107 y
108 108 y
109 109 EOF
110 110
111 111 echo % modify end of plain file, no EOL
112 112
113 113 hg tip --template '{node}' >> plain
114 114 hg record -d '9 0' -m noeol plain <<EOF
115 115 y
116 116 y
117 117 EOF
118 118
119 119 echo % modify end of plain file, add EOL
120 120
121 121 echo >> plain
122 122 hg record -d '10 0' -m eol plain <<EOF
123 123 y
124 124 y
125 125 y
126 126 EOF
127 127
128 128 echo % modify beginning, trim end, record both
129 129
130 130 rm plain
131 131 for i in 2 2 3 4 5 6 7 8 9 10; do
132 132 echo $i >> plain
133 133 done
134 134
135 135 hg record -d '10 0' -m begin-and-end plain <<EOF
136 136 y
137 137 y
138 138 y
139 139 EOF
140 140 echo; hg tip -p
141 141
142 142 echo % trim beginning, modify end
143 143
144 144 rm plain
145 145 for i in 4 5 6 7 8 9 10.new; do
146 146 echo $i >> plain
147 147 done
148 148
149 149 echo % record end
150 150
151 151 hg record -d '11 0' -m end-only plain <<EOF
152 152 y
153 153 n
154 154 y
155 155 EOF
156 156 echo; hg tip -p
157 157
158 158 echo % record beginning
159 159
160 160 hg record -d '12 0' -m begin-only plain <<EOF
161 161 y
162 162 y
163 163 EOF
164 164 echo; hg tip -p
165 165
166 166 echo % add to beginning, trim from end
167 167
168 168 rm plain
169 169 for i in 1 2 3 4 5 6 7 8 9; do
170 170 echo $i >> plain
171 171 done
172 172
173 173 echo % record end
174 174
175 175 hg record --traceback -d '13 0' -m end-again plain<<EOF
176 176 y
177 177 n
178 178 y
179 179 EOF
180 180
181 181 echo % add to beginning, middle, end
182 182
183 183 rm plain
184 184 for i in 1 2 3 4 5 5.new 5.reallynew 6 7 8 9 10 11; do
185 185 echo $i >> plain
186 186 done
187 187
188 188 echo % record beginning, middle
189 189
190 190 hg record -d '14 0' -m middle-only plain <<EOF
191 191 y
192 192 y
193 193 y
194 194 n
195 195 EOF
196 196 echo; hg tip -p
197 197
198 198 echo % record end
199 199
200 200 hg record -d '15 0' -m end-only plain <<EOF
201 201 y
202 202 y
203 203 EOF
204 204 echo; hg tip -p
205 205
206 206 mkdir subdir
207 207 cd subdir
208 208 echo a > a
209 209 hg ci -d '16 0' -Amsubdir
210 210
211 211 echo a >> a
212 212 hg record -d '16 0' -m subdir-change a <<EOF
213 213 y
214 214 y
215 215 EOF
216 216 echo; hg tip -p
217 217
218 218 echo a > f1
219 219 echo b > f2
220 220 hg add f1 f2
221 221
222 222 hg ci -mz -d '17 0'
223 223
224 224 echo a >> f1
225 225 echo b >> f2
226 226
227 227 echo % help, quit
228 228
229 229 hg record <<EOF
230 230 ?
231 231 q
232 232 EOF
233 233
234 234 echo % skip
235 235
236 236 hg record <<EOF
237 237 s
238 238 EOF
239 239
240 240 echo % no
241 241
242 242 hg record <<EOF
243 243 n
244 244 EOF
245 245
246 246 echo % f, quit
247 247
248 248 hg record <<EOF
249 249 f
250 250 q
251 251 EOF
252 252
253 253 echo % s, all
254 254
255 255 hg record -d '18 0' -mx <<EOF
256 256 s
257 257 a
258 258 EOF
259 259 echo; hg tip -p
260 260
261 261 echo % f
262 262
263 263 hg record -d '19 0' -my <<EOF
264 264 f
265 265 EOF
266 266 echo; hg tip -p
267 267
268 268 echo % preserve chmod +x
269 269
270 270 chmod +x f1
271 271 echo a >> f1
272 272 hg record -d '20 0' -mz <<EOF
273 273 y
274 274 y
275 275 y
276 276 EOF
277 277 echo; hg tip --config diff.git=True -p
278 278
279 279 echo % preserve execute permission on original
280 280
281 281 echo b >> f1
282 282 hg record -d '21 0' -maa <<EOF
283 283 y
284 284 y
285 285 y
286 286 EOF
287 287 echo; hg tip --config diff.git=True -p
288 288
289 289 echo % preserve chmod -x
290 290
291 291 chmod -x f1
292 292 echo c >> f1
293 293 hg record -d '22 0' -mab <<EOF
294 294 y
295 295 y
296 296 y
297 297 EOF
298 298 echo; hg tip --config diff.git=True -p
299 299
300 cd ..
301
302 echo % abort early when a merge is in progress
303 hg up 4
304 touch iwillmergethat
305 hg add iwillmergethat
306 hg branch thatbranch
307 hg ci -m'new head'
308 hg up default
309 hg merge thatbranch
310 echo; hg record -m'will abort'
311 hg up -C
300 312
301 313 echo % with win32ext
302 cd ..
303 314 echo '[extensions]' >> .hg/hgrc
304 315 echo 'win32text = ' >> .hg/hgrc
305 316 echo '[decode]' >> .hg/hgrc
306 317 echo '** = cleverdecode:' >> .hg/hgrc
307 318 echo '[encode]' >> .hg/hgrc
308 319 echo '** = cleverencode:' >> .hg/hgrc
309 320 echo '[patch]' >> .hg/hgrc
310 321 echo 'eol = crlf' >> .hg/hgrc
311 322
312 323 echo d >> subdir/f1
313 324 hg record -d '23 0' -mw1 <<EOF
314 325 y
315 326 y
316 327 EOF
317 328 echo; hg tip -p
318 329
@@ -1,595 +1,608
1 1 % help
2 2 hg record [OPTION]... [FILE]...
3 3
4 4 interactively select changes to commit
5 5
6 6 If a list of files is omitted, all changes reported by "hg status" will be
7 7 candidates for recording.
8 8
9 9 See 'hg help dates' for a list of formats valid for -d/--date.
10 10
11 11 You will be prompted for whether to record changes to each modified file,
12 12 and for files with multiple changes, for each change to use. For each
13 13 query, the following responses are possible:
14 14
15 15 y - record this change
16 16 n - skip this change
17 17
18 18 s - skip remaining changes to this file
19 19 f - record remaining changes to this file
20 20
21 21 d - done, skip remaining changes and files
22 22 a - record all changes to all remaining files
23 23 q - quit, recording no changes
24 24
25 25 ? - display help
26 26
27 This command is not available when committing a merge.
28
27 29 options:
28 30
29 31 -A --addremove mark new/missing files as added/removed before committing
30 32 --close-branch mark a branch as closed, hiding it from the branch list
31 33 -I --include include names matching the given patterns
32 34 -X --exclude exclude names matching the given patterns
33 35 -m --message use <text> as commit message
34 36 -l --logfile read commit message from <file>
35 37 -d --date record datecode as commit date
36 38 -u --user record the specified user as committer
37 39
38 40 use "hg -v help record" to show global options
39 41 % select no files
40 42 diff --git a/empty-rw b/empty-rw
41 43 new file mode 100644
42 44 examine changes to 'empty-rw'? [Ynsfdaq?] no changes to record
43 45
44 46 changeset: -1:000000000000
45 47 tag: tip
46 48 user:
47 49 date: Thu Jan 01 00:00:00 1970 +0000
48 50
49 51
50 52 % select files but no hunks
51 53 diff --git a/empty-rw b/empty-rw
52 54 new file mode 100644
53 55 examine changes to 'empty-rw'? [Ynsfdaq?] abort: empty commit message
54 56
55 57 changeset: -1:000000000000
56 58 tag: tip
57 59 user:
58 60 date: Thu Jan 01 00:00:00 1970 +0000
59 61
60 62
61 63 % record empty file
62 64 diff --git a/empty-rw b/empty-rw
63 65 new file mode 100644
64 66 examine changes to 'empty-rw'? [Ynsfdaq?]
65 67 changeset: 0:c0708cf4e46e
66 68 tag: tip
67 69 user: test
68 70 date: Thu Jan 01 00:00:00 1970 +0000
69 71 summary: empty
70 72
71 73
72 74 % rename empty file
73 75 diff --git a/empty-rw b/empty-rename
74 76 rename from empty-rw
75 77 rename to empty-rename
76 78 examine changes to 'empty-rw' and 'empty-rename'? [Ynsfdaq?]
77 79 changeset: 1:d695e8dcb197
78 80 tag: tip
79 81 user: test
80 82 date: Thu Jan 01 00:00:01 1970 +0000
81 83 summary: rename
82 84
83 85
84 86 % copy empty file
85 87 diff --git a/empty-rename b/empty-copy
86 88 copy from empty-rename
87 89 copy to empty-copy
88 90 examine changes to 'empty-rename' and 'empty-copy'? [Ynsfdaq?]
89 91 changeset: 2:1d4b90bea524
90 92 tag: tip
91 93 user: test
92 94 date: Thu Jan 01 00:00:02 1970 +0000
93 95 summary: copy
94 96
95 97
96 98 % delete empty file
97 99 diff --git a/empty-copy b/empty-copy
98 100 deleted file mode 100644
99 101 examine changes to 'empty-copy'? [Ynsfdaq?]
100 102 changeset: 3:b39a238f01a1
101 103 tag: tip
102 104 user: test
103 105 date: Thu Jan 01 00:00:03 1970 +0000
104 106 summary: delete
105 107
106 108
107 109 % add binary file
108 110 1 changesets found
109 111 diff --git a/tip.bundle b/tip.bundle
110 112 new file mode 100644
111 113 this is a binary file
112 114 examine changes to 'tip.bundle'? [Ynsfdaq?]
113 115 changeset: 4:ad816da3711e
114 116 tag: tip
115 117 user: test
116 118 date: Thu Jan 01 00:00:04 1970 +0000
117 119 summary: binary
118 120
119 121 diff -r b39a238f01a1 -r ad816da3711e tip.bundle
120 122 Binary file tip.bundle has changed
121 123
122 124 % change binary file
123 125 1 changesets found
124 126 diff --git a/tip.bundle b/tip.bundle
125 127 this modifies a binary file (all or nothing)
126 128 examine changes to 'tip.bundle'? [Ynsfdaq?]
127 129 changeset: 5:dccd6f3eb485
128 130 tag: tip
129 131 user: test
130 132 date: Thu Jan 01 00:00:05 1970 +0000
131 133 summary: binary-change
132 134
133 135 diff -r ad816da3711e -r dccd6f3eb485 tip.bundle
134 136 Binary file tip.bundle has changed
135 137
136 138 % rename and change binary file
137 139 1 changesets found
138 140 diff --git a/tip.bundle b/top.bundle
139 141 rename from tip.bundle
140 142 rename to top.bundle
141 143 this modifies a binary file (all or nothing)
142 144 examine changes to 'tip.bundle' and 'top.bundle'? [Ynsfdaq?]
143 145 changeset: 6:7fa44105f5b3
144 146 tag: tip
145 147 user: test
146 148 date: Thu Jan 01 00:00:06 1970 +0000
147 149 summary: binary-change-rename
148 150
149 151 diff -r dccd6f3eb485 -r 7fa44105f5b3 tip.bundle
150 152 Binary file tip.bundle has changed
151 153 diff -r dccd6f3eb485 -r 7fa44105f5b3 top.bundle
152 154 Binary file top.bundle has changed
153 155
154 156 % add plain file
155 157 diff --git a/plain b/plain
156 158 new file mode 100644
157 159 examine changes to 'plain'? [Ynsfdaq?]
158 160 changeset: 7:11fb457c1be4
159 161 tag: tip
160 162 user: test
161 163 date: Thu Jan 01 00:00:07 1970 +0000
162 164 summary: plain
163 165
164 166 diff -r 7fa44105f5b3 -r 11fb457c1be4 plain
165 167 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
166 168 +++ b/plain Thu Jan 01 00:00:07 1970 +0000
167 169 @@ -0,0 +1,10 @@
168 170 +1
169 171 +2
170 172 +3
171 173 +4
172 174 +5
173 175 +6
174 176 +7
175 177 +8
176 178 +9
177 179 +10
178 180
179 181 % modify end of plain file
180 182 diff --git a/plain b/plain
181 183 1 hunks, 1 lines changed
182 184 examine changes to 'plain'? [Ynsfdaq?] @@ -8,3 +8,4 @@
183 185 8
184 186 9
185 187 10
186 188 +11
187 189 record this change to 'plain'? [Ynsfdaq?] % modify end of plain file, no EOL
188 190 diff --git a/plain b/plain
189 191 1 hunks, 1 lines changed
190 192 examine changes to 'plain'? [Ynsfdaq?] @@ -9,3 +9,4 @@
191 193 9
192 194 10
193 195 11
194 196 +7264f99c5f5ff3261504828afa4fb4d406c3af54
195 197 \ No newline at end of file
196 198 record this change to 'plain'? [Ynsfdaq?] % modify end of plain file, add EOL
197 199 diff --git a/plain b/plain
198 200 1 hunks, 2 lines changed
199 201 examine changes to 'plain'? [Ynsfdaq?] @@ -9,4 +9,4 @@
200 202 9
201 203 10
202 204 11
203 205 -7264f99c5f5ff3261504828afa4fb4d406c3af54
204 206 \ No newline at end of file
205 207 +7264f99c5f5ff3261504828afa4fb4d406c3af54
206 208 record this change to 'plain'? [Ynsfdaq?] % modify beginning, trim end, record both
207 209 diff --git a/plain b/plain
208 210 2 hunks, 4 lines changed
209 211 examine changes to 'plain'? [Ynsfdaq?] @@ -1,4 +1,4 @@
210 212 -1
211 213 +2
212 214 2
213 215 3
214 216 4
215 217 record change 1/2 to 'plain'? [Ynsfdaq?] @@ -8,5 +8,3 @@
216 218 8
217 219 9
218 220 10
219 221 -11
220 222 -7264f99c5f5ff3261504828afa4fb4d406c3af54
221 223 record change 2/2 to 'plain'? [Ynsfdaq?]
222 224 changeset: 11:efca65c9b09e
223 225 tag: tip
224 226 user: test
225 227 date: Thu Jan 01 00:00:10 1970 +0000
226 228 summary: begin-and-end
227 229
228 230 diff -r cd07d48e8cbe -r efca65c9b09e plain
229 231 --- a/plain Thu Jan 01 00:00:10 1970 +0000
230 232 +++ b/plain Thu Jan 01 00:00:10 1970 +0000
231 233 @@ -1,4 +1,4 @@
232 234 -1
233 235 +2
234 236 2
235 237 3
236 238 4
237 239 @@ -8,5 +8,3 @@
238 240 8
239 241 9
240 242 10
241 243 -11
242 244 -7264f99c5f5ff3261504828afa4fb4d406c3af54
243 245
244 246 % trim beginning, modify end
245 247 % record end
246 248 diff --git a/plain b/plain
247 249 2 hunks, 5 lines changed
248 250 examine changes to 'plain'? [Ynsfdaq?] @@ -1,9 +1,6 @@
249 251 -2
250 252 -2
251 253 -3
252 254 4
253 255 5
254 256 6
255 257 7
256 258 8
257 259 9
258 260 record change 1/2 to 'plain'? [Ynsfdaq?] @@ -4,7 +1,7 @@
259 261 4
260 262 5
261 263 6
262 264 7
263 265 8
264 266 9
265 267 -10
266 268 +10.new
267 269 record change 2/2 to 'plain'? [Ynsfdaq?]
268 270 changeset: 12:7d1e66983c15
269 271 tag: tip
270 272 user: test
271 273 date: Thu Jan 01 00:00:11 1970 +0000
272 274 summary: end-only
273 275
274 276 diff -r efca65c9b09e -r 7d1e66983c15 plain
275 277 --- a/plain Thu Jan 01 00:00:10 1970 +0000
276 278 +++ b/plain Thu Jan 01 00:00:11 1970 +0000
277 279 @@ -7,4 +7,4 @@
278 280 7
279 281 8
280 282 9
281 283 -10
282 284 +10.new
283 285
284 286 % record beginning
285 287 diff --git a/plain b/plain
286 288 1 hunks, 3 lines changed
287 289 examine changes to 'plain'? [Ynsfdaq?] @@ -1,6 +1,3 @@
288 290 -2
289 291 -2
290 292 -3
291 293 4
292 294 5
293 295 6
294 296 record this change to 'plain'? [Ynsfdaq?]
295 297 changeset: 13:a09fc62a0e61
296 298 tag: tip
297 299 user: test
298 300 date: Thu Jan 01 00:00:12 1970 +0000
299 301 summary: begin-only
300 302
301 303 diff -r 7d1e66983c15 -r a09fc62a0e61 plain
302 304 --- a/plain Thu Jan 01 00:00:11 1970 +0000
303 305 +++ b/plain Thu Jan 01 00:00:12 1970 +0000
304 306 @@ -1,6 +1,3 @@
305 307 -2
306 308 -2
307 309 -3
308 310 4
309 311 5
310 312 6
311 313
312 314 % add to beginning, trim from end
313 315 % record end
314 316 diff --git a/plain b/plain
315 317 2 hunks, 4 lines changed
316 318 examine changes to 'plain'? [Ynsfdaq?] @@ -1,6 +1,9 @@
317 319 +1
318 320 +2
319 321 +3
320 322 4
321 323 5
322 324 6
323 325 7
324 326 8
325 327 9
326 328 record change 1/2 to 'plain'? [Ynsfdaq?] @@ -1,7 +4,6 @@
327 329 4
328 330 5
329 331 6
330 332 7
331 333 8
332 334 9
333 335 -10.new
334 336 record change 2/2 to 'plain'? [Ynsfdaq?] % add to beginning, middle, end
335 337 % record beginning, middle
336 338 diff --git a/plain b/plain
337 339 3 hunks, 7 lines changed
338 340 examine changes to 'plain'? [Ynsfdaq?] @@ -1,2 +1,5 @@
339 341 +1
340 342 +2
341 343 +3
342 344 4
343 345 5
344 346 record change 1/3 to 'plain'? [Ynsfdaq?] @@ -1,6 +4,8 @@
345 347 4
346 348 5
347 349 +5.new
348 350 +5.reallynew
349 351 6
350 352 7
351 353 8
352 354 9
353 355 record change 2/3 to 'plain'? [Ynsfdaq?] @@ -3,4 +8,6 @@
354 356 6
355 357 7
356 358 8
357 359 9
358 360 +10
359 361 +11
360 362 record change 3/3 to 'plain'? [Ynsfdaq?]
361 363 changeset: 15:7d137997f3a6
362 364 tag: tip
363 365 user: test
364 366 date: Thu Jan 01 00:00:14 1970 +0000
365 367 summary: middle-only
366 368
367 369 diff -r c0b8e5fb0be6 -r 7d137997f3a6 plain
368 370 --- a/plain Thu Jan 01 00:00:13 1970 +0000
369 371 +++ b/plain Thu Jan 01 00:00:14 1970 +0000
370 372 @@ -1,5 +1,10 @@
371 373 +1
372 374 +2
373 375 +3
374 376 4
375 377 5
376 378 +5.new
377 379 +5.reallynew
378 380 6
379 381 7
380 382 8
381 383
382 384 % record end
383 385 diff --git a/plain b/plain
384 386 1 hunks, 2 lines changed
385 387 examine changes to 'plain'? [Ynsfdaq?] @@ -9,3 +9,5 @@
386 388 7
387 389 8
388 390 9
389 391 +10
390 392 +11
391 393 record this change to 'plain'? [Ynsfdaq?]
392 394 changeset: 16:4959e3ff13eb
393 395 tag: tip
394 396 user: test
395 397 date: Thu Jan 01 00:00:15 1970 +0000
396 398 summary: end-only
397 399
398 400 diff -r 7d137997f3a6 -r 4959e3ff13eb plain
399 401 --- a/plain Thu Jan 01 00:00:14 1970 +0000
400 402 +++ b/plain Thu Jan 01 00:00:15 1970 +0000
401 403 @@ -9,3 +9,5 @@
402 404 7
403 405 8
404 406 9
405 407 +10
406 408 +11
407 409
408 410 adding subdir/a
409 411 diff --git a/subdir/a b/subdir/a
410 412 1 hunks, 1 lines changed
411 413 examine changes to 'subdir/a'? [Ynsfdaq?] @@ -1,1 +1,2 @@
412 414 a
413 415 +a
414 416 record this change to 'subdir/a'? [Ynsfdaq?]
415 417 changeset: 18:40698cd490b2
416 418 tag: tip
417 419 user: test
418 420 date: Thu Jan 01 00:00:16 1970 +0000
419 421 summary: subdir-change
420 422
421 423 diff -r 661eacdc08b9 -r 40698cd490b2 subdir/a
422 424 --- a/subdir/a Thu Jan 01 00:00:16 1970 +0000
423 425 +++ b/subdir/a Thu Jan 01 00:00:16 1970 +0000
424 426 @@ -1,1 +1,2 @@
425 427 a
426 428 +a
427 429
428 430 % help, quit
429 431 diff --git a/subdir/f1 b/subdir/f1
430 432 1 hunks, 1 lines changed
431 433 examine changes to 'subdir/f1'? [Ynsfdaq?] y - record this change
432 434 n - skip this change
433 435 s - skip remaining changes to this file
434 436 f - record remaining changes to this file
435 437 d - done, skip remaining changes and files
436 438 a - record all changes to all remaining files
437 439 q - quit, recording no changes
438 440 ? - display help
439 441 examine changes to 'subdir/f1'? [Ynsfdaq?] abort: user quit
440 442 % skip
441 443 diff --git a/subdir/f1 b/subdir/f1
442 444 1 hunks, 1 lines changed
443 445 examine changes to 'subdir/f1'? [Ynsfdaq?] diff --git a/subdir/f2 b/subdir/f2
444 446 1 hunks, 1 lines changed
445 447 examine changes to 'subdir/f2'? [Ynsfdaq?] abort: response expected
446 448 % no
447 449 diff --git a/subdir/f1 b/subdir/f1
448 450 1 hunks, 1 lines changed
449 451 examine changes to 'subdir/f1'? [Ynsfdaq?] diff --git a/subdir/f2 b/subdir/f2
450 452 1 hunks, 1 lines changed
451 453 examine changes to 'subdir/f2'? [Ynsfdaq?] abort: response expected
452 454 % f, quit
453 455 diff --git a/subdir/f1 b/subdir/f1
454 456 1 hunks, 1 lines changed
455 457 examine changes to 'subdir/f1'? [Ynsfdaq?] diff --git a/subdir/f2 b/subdir/f2
456 458 1 hunks, 1 lines changed
457 459 examine changes to 'subdir/f2'? [Ynsfdaq?] abort: user quit
458 460 % s, all
459 461 diff --git a/subdir/f1 b/subdir/f1
460 462 1 hunks, 1 lines changed
461 463 examine changes to 'subdir/f1'? [Ynsfdaq?] diff --git a/subdir/f2 b/subdir/f2
462 464 1 hunks, 1 lines changed
463 465 examine changes to 'subdir/f2'? [Ynsfdaq?]
464 466 changeset: 20:d2d8c25276a8
465 467 tag: tip
466 468 user: test
467 469 date: Thu Jan 01 00:00:18 1970 +0000
468 470 summary: x
469 471
470 472 diff -r 25eb2a7694fb -r d2d8c25276a8 subdir/f2
471 473 --- a/subdir/f2 Thu Jan 01 00:00:17 1970 +0000
472 474 +++ b/subdir/f2 Thu Jan 01 00:00:18 1970 +0000
473 475 @@ -1,1 +1,2 @@
474 476 b
475 477 +b
476 478
477 479 % f
478 480 diff --git a/subdir/f1 b/subdir/f1
479 481 1 hunks, 1 lines changed
480 482 examine changes to 'subdir/f1'? [Ynsfdaq?]
481 483 changeset: 21:1013f51ce32f
482 484 tag: tip
483 485 user: test
484 486 date: Thu Jan 01 00:00:19 1970 +0000
485 487 summary: y
486 488
487 489 diff -r d2d8c25276a8 -r 1013f51ce32f subdir/f1
488 490 --- a/subdir/f1 Thu Jan 01 00:00:18 1970 +0000
489 491 +++ b/subdir/f1 Thu Jan 01 00:00:19 1970 +0000
490 492 @@ -1,1 +1,2 @@
491 493 a
492 494 +a
493 495
494 496 % preserve chmod +x
495 497 diff --git a/subdir/f1 b/subdir/f1
496 498 old mode 100644
497 499 new mode 100755
498 500 1 hunks, 1 lines changed
499 501 examine changes to 'subdir/f1'? [Ynsfdaq?] @@ -1,2 +1,3 @@
500 502 a
501 503 a
502 504 +a
503 505 record this change to 'subdir/f1'? [Ynsfdaq?]
504 506 changeset: 22:5df857735621
505 507 tag: tip
506 508 user: test
507 509 date: Thu Jan 01 00:00:20 1970 +0000
508 510 summary: z
509 511
510 512 diff --git a/subdir/f1 b/subdir/f1
511 513 old mode 100644
512 514 new mode 100755
513 515 --- a/subdir/f1
514 516 +++ b/subdir/f1
515 517 @@ -1,2 +1,3 @@
516 518 a
517 519 a
518 520 +a
519 521
520 522 % preserve execute permission on original
521 523 diff --git a/subdir/f1 b/subdir/f1
522 524 1 hunks, 1 lines changed
523 525 examine changes to 'subdir/f1'? [Ynsfdaq?] @@ -1,3 +1,4 @@
524 526 a
525 527 a
526 528 a
527 529 +b
528 530 record this change to 'subdir/f1'? [Ynsfdaq?]
529 531 changeset: 23:a4ae36a78715
530 532 tag: tip
531 533 user: test
532 534 date: Thu Jan 01 00:00:21 1970 +0000
533 535 summary: aa
534 536
535 537 diff --git a/subdir/f1 b/subdir/f1
536 538 --- a/subdir/f1
537 539 +++ b/subdir/f1
538 540 @@ -1,3 +1,4 @@
539 541 a
540 542 a
541 543 a
542 544 +b
543 545
544 546 % preserve chmod -x
545 547 diff --git a/subdir/f1 b/subdir/f1
546 548 old mode 100755
547 549 new mode 100644
548 550 1 hunks, 1 lines changed
549 551 examine changes to 'subdir/f1'? [Ynsfdaq?] @@ -2,3 +2,4 @@
550 552 a
551 553 a
552 554 b
553 555 +c
554 556 record this change to 'subdir/f1'? [Ynsfdaq?]
555 557 changeset: 24:1460f6e47966
556 558 tag: tip
557 559 user: test
558 560 date: Thu Jan 01 00:00:22 1970 +0000
559 561 summary: ab
560 562
561 563 diff --git a/subdir/f1 b/subdir/f1
562 564 old mode 100755
563 565 new mode 100644
564 566 --- a/subdir/f1
565 567 +++ b/subdir/f1
566 568 @@ -2,3 +2,4 @@
567 569 a
568 570 a
569 571 b
570 572 +c
571 573
574 % abort early when a merge is in progress
575 1 files updated, 0 files merged, 5 files removed, 0 files unresolved
576 marked working directory as branch thatbranch
577 created new head
578 5 files updated, 0 files merged, 2 files removed, 0 files unresolved
579 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
580 (branch merge, don't forget to commit)
581
582 abort: cannot partially commit a merge (use hg commit instead)
583 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
572 584 % with win32ext
573 585 diff --git a/subdir/f1 b/subdir/f1
574 586 1 hunks, 1 lines changed
575 587 examine changes to 'subdir/f1'? [Ynsfdaq?] @@ -3,3 +3,4 @@
576 588 a
577 589 b
578 590 c
579 591 +d
580 592 record this change to 'subdir/f1'? [Ynsfdaq?]
581 changeset: 25:5bacc1f6e9cf
593 changeset: 26:5bacc1f6e9cf
582 594 tag: tip
595 parent: 24:1460f6e47966
583 596 user: test
584 597 date: Thu Jan 01 00:00:23 1970 +0000
585 598 summary: w1
586 599
587 600 diff -r 1460f6e47966 -r 5bacc1f6e9cf subdir/f1
588 601 --- a/subdir/f1 Thu Jan 01 00:00:22 1970 +0000
589 602 +++ b/subdir/f1 Thu Jan 01 00:00:23 1970 +0000
590 603 @@ -3,3 +3,4 @@
591 604 a
592 605 b
593 606 c
594 607 +d
595 608
General Comments 0
You need to be logged in to leave comments. Login now