Mercurial > public > mercurial-scm > hg
comparison mercurial/localrepo.py @ 42141:0e41f40b01cc
copies: add config option for writing copy metadata to file and/or changset
This introduces a config option that lets you choose to write copy
metadata to the changeset extras instead of to filelog. There's also
an option to write it to both places. I imagine that may possibly be
useful when transitioning an existing repo.
The copy metadata is stored as two fields in extras: one for copies
since p1 and one for copies since p2.
I may need to add more information later in order to make copy tracing
faster. Specifically, I'm thinking out recording which files were
added or removed so that copies._chaincopies() doesn't have to look at
the manifest for that. But that would just be an optimization and that
can be added once we know if it's necessary.
I have also considered saving space by using replacing the destination
file path by an index into the "files" list, but that can also be
changed later (but before the feature is ready to release).
Differential Revision: https://phab.mercurial-scm.org/D6183
author | Martin von Zweigbergk <martinvonz@google.com> |
---|---|
date | Wed, 27 Dec 2017 19:49:36 -0800 |
parents | 10a6725dca6e |
children | d345627d104b c2b83c957621 |
comparison
equal
deleted
inserted
replaced
42140:a4483e380c3e | 42141:0e41f40b01cc |
---|---|
2322 | 2322 |
2323 def currentwlock(self): | 2323 def currentwlock(self): |
2324 """Returns the wlock if it's held, or None if it's not.""" | 2324 """Returns the wlock if it's held, or None if it's not.""" |
2325 return self._currentlock(self._wlockref) | 2325 return self._currentlock(self._wlockref) |
2326 | 2326 |
2327 def _filecommit(self, fctx, manifest1, manifest2, linkrev, tr, changelist): | 2327 def _filecommit(self, fctx, manifest1, manifest2, linkrev, tr, changelist, |
2328 includecopymeta): | |
2328 """ | 2329 """ |
2329 commit an individual file as part of a larger transaction | 2330 commit an individual file as part of a larger transaction |
2330 """ | 2331 """ |
2331 | 2332 |
2332 fname = fctx.path() | 2333 fname = fctx.path() |
2381 # expect this outcome it can be fixed, but this is the correct | 2382 # expect this outcome it can be fixed, but this is the correct |
2382 # behavior in this circumstance. | 2383 # behavior in this circumstance. |
2383 | 2384 |
2384 if cnode: | 2385 if cnode: |
2385 self.ui.debug(" %s: copy %s:%s\n" % (fname, cfname, hex(cnode))) | 2386 self.ui.debug(" %s: copy %s:%s\n" % (fname, cfname, hex(cnode))) |
2386 meta["copy"] = cfname | 2387 if includecopymeta: |
2387 meta["copyrev"] = hex(cnode) | 2388 meta["copy"] = cfname |
2389 meta["copyrev"] = hex(cnode) | |
2388 fparent1, fparent2 = nullid, newfparent | 2390 fparent1, fparent2 = nullid, newfparent |
2389 else: | 2391 else: |
2390 self.ui.warn(_("warning: can't find ancestor for '%s' " | 2392 self.ui.warn(_("warning: can't find ancestor for '%s' " |
2391 "copied from '%s'!\n") % (fname, cfname)) | 2393 "copied from '%s'!\n") % (fname, cfname)) |
2392 | 2394 |
2550 """ | 2552 """ |
2551 | 2553 |
2552 p1, p2 = ctx.p1(), ctx.p2() | 2554 p1, p2 = ctx.p1(), ctx.p2() |
2553 user = ctx.user() | 2555 user = ctx.user() |
2554 | 2556 |
2557 writecopiesto = self.ui.config('experimental', 'copies.write-to') | |
2558 writefilecopymeta = writecopiesto != 'changeset-only' | |
2559 p1copies, p2copies = None, None | |
2560 if writecopiesto in ('changeset-only', 'compatibility'): | |
2561 p1copies = ctx.p1copies() | |
2562 p2copies = ctx.p2copies() | |
2555 with self.lock(), self.transaction("commit") as tr: | 2563 with self.lock(), self.transaction("commit") as tr: |
2556 trp = weakref.proxy(tr) | 2564 trp = weakref.proxy(tr) |
2557 | 2565 |
2558 if ctx.manifestnode(): | 2566 if ctx.manifestnode(): |
2559 # reuse an existing manifest revision | 2567 # reuse an existing manifest revision |
2583 if fctx is None: | 2591 if fctx is None: |
2584 removed.append(f) | 2592 removed.append(f) |
2585 else: | 2593 else: |
2586 added.append(f) | 2594 added.append(f) |
2587 m[f] = self._filecommit(fctx, m1, m2, linkrev, | 2595 m[f] = self._filecommit(fctx, m1, m2, linkrev, |
2588 trp, changed) | 2596 trp, changed, |
2597 writefilecopymeta) | |
2589 m.setflag(f, fctx.flags()) | 2598 m.setflag(f, fctx.flags()) |
2590 except OSError: | 2599 except OSError: |
2591 self.ui.warn(_("trouble committing %s!\n") % | 2600 self.ui.warn(_("trouble committing %s!\n") % |
2592 uipathfn(f)) | 2601 uipathfn(f)) |
2593 raise | 2602 raise |
2637 # update changelog | 2646 # update changelog |
2638 self.ui.note(_("committing changelog\n")) | 2647 self.ui.note(_("committing changelog\n")) |
2639 self.changelog.delayupdate(tr) | 2648 self.changelog.delayupdate(tr) |
2640 n = self.changelog.add(mn, files, ctx.description(), | 2649 n = self.changelog.add(mn, files, ctx.description(), |
2641 trp, p1.node(), p2.node(), | 2650 trp, p1.node(), p2.node(), |
2642 user, ctx.date(), ctx.extra().copy()) | 2651 user, ctx.date(), ctx.extra().copy(), |
2652 p1copies, p2copies) | |
2643 xp1, xp2 = p1.hex(), p2 and p2.hex() or '' | 2653 xp1, xp2 = p1.hex(), p2 and p2.hex() or '' |
2644 self.hook('pretxncommit', throw=True, node=hex(n), parent1=xp1, | 2654 self.hook('pretxncommit', throw=True, node=hex(n), parent1=xp1, |
2645 parent2=xp2) | 2655 parent2=xp2) |
2646 # set the new commit is proper phase | 2656 # set the new commit is proper phase |
2647 targetphase = subrepoutil.newcommitphase(self.ui, ctx) | 2657 targetphase = subrepoutil.newcommitphase(self.ui, ctx) |