Patchwork D9002: mergestate: introduce a new ACTION_KEEP_NEW

login
register
mail settings
Submitter phabricator
Date Sept. 9, 2020, 1:44 p.m.
Message ID <differential-rev-PHID-DREV-swulp7xbomh3dymypmx4-req@mercurial-scm.org>
Download mbox | patch
Permalink /patch/47114/
State Superseded
Headers show

Comments

phabricator - Sept. 9, 2020, 1:44 p.m.
pulkit created this revision.
Herald added a reviewer: hg-reviewers.
Herald added a subscriber: mercurial-patches.

REVISION SUMMARY
  `ACTION_KEEP` is overloaded and it's hard to figure out how we end up with this
  KEEP, what was the state of things.
  
  In a previous patch, we introduced `ACTION_KEEP_ABSENT` which represents files
  which are kept absent in the working directory.
  
  There is another special case where we keep the file when it's not present on
  both ancestor and remote side. We introduce a dedicated action for that.
  
  The goal is to use these information to make bid merge smarter.

REPOSITORY
  rHG Mercurial

BRANCH
  default

REVISION DETAIL
  https://phab.mercurial-scm.org/D9002

AFFECTED FILES
  mercurial/merge.py
  mercurial/mergestate.py
  tests/test-merge-criss-cross.t

CHANGE DETAILS




To: pulkit, #hg-reviewers
Cc: mercurial-patches, mercurial-devel

Patch

diff --git a/tests/test-merge-criss-cross.t b/tests/test-merge-criss-cross.t
--- a/tests/test-merge-criss-cross.t
+++ b/tests/test-merge-criss-cross.t
@@ -446,8 +446,8 @@ 
   resolving manifests
    branchmerge: True, force: False, partial: False
    ancestor: 11b5b303e36c, local: c0ef19750a22+, remote: 6ca01f7342b9
-   d1/a: ancestor missing, remote missing -> k
-   d1/b: ancestor missing, remote missing -> k
+   d1/a: ancestor missing, remote missing -> kn
+   d1/b: ancestor missing, remote missing -> kn
    d2/b: remote created -> g
   
   calculating bids for ancestor 154e6000f54e
@@ -468,14 +468,14 @@ 
   auction for merging merge bids (2 ancestors)
    d1/a:
      list of bids:
-       ancestor missing, remote missing -> k
+       ancestor missing, remote missing -> kn
        other deleted -> r
-     picking 'keep' action
+   d1/a: picking 'keep new' action
    d1/b:
      list of bids:
-       ancestor missing, remote missing -> k
+       ancestor missing, remote missing -> kn
        other deleted -> r
-     picking 'keep' action
+   d1/b: picking 'keep new' action
    d2/b:
      list of bids:
        remote created -> g
@@ -485,8 +485,8 @@ 
   
    d2/b: remote created -> g
   getting d2/b
-   d1/a: ancestor missing, remote missing -> k
-   d1/b: ancestor missing, remote missing -> k
+   d1/a: ancestor missing, remote missing -> kn
+   d1/b: ancestor missing, remote missing -> kn
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
   (branch merge, don't forget to commit)
 
diff --git a/mercurial/mergestate.py b/mercurial/mergestate.py
--- a/mercurial/mergestate.py
+++ b/mercurial/mergestate.py
@@ -124,6 +124,9 @@ 
 # keep it absent (absent means file not present, it can be a result
 # of file deletion, rename etc.)
 ACTION_KEEP_ABSENT = b'ka'
+# the file is absent on the ancestor and remote side of the merge
+# hence this file is new and we should keep it
+ACTION_KEEP_NEW = b'kn'
 ACTION_EXEC = b'e'
 ACTION_CREATED_MERGE = b'cm'
 
@@ -845,6 +848,10 @@ 
     for f, args, msg in actions.get(ACTION_KEEP_ABSENT, []):
         pass
 
+    # keep new
+    for f, args, msg in actions.get(ACTION_KEEP_NEW, []):
+        pass
+
     # get
     for f, args, msg in actions.get(ACTION_GET, []):
         if branchmerge:
diff --git a/mercurial/merge.py b/mercurial/merge.py
--- a/mercurial/merge.py
+++ b/mercurial/merge.py
@@ -566,6 +566,7 @@ 
     NO_OP_ACTIONS = (
         mergestatemod.ACTION_KEEP,
         mergestatemod.ACTION_KEEP_ABSENT,
+        mergestatemod.ACTION_KEEP_NEW,
     )
 
     def __init__(self):
@@ -964,7 +965,7 @@ 
                 if not rename_found:
                     mresult.addfile(
                         f,
-                        mergestatemod.ACTION_KEEP,
+                        mergestatemod.ACTION_KEEP_NEW,
                         None,
                         b'ancestor missing, remote missing',
                     )
@@ -1237,6 +1238,11 @@ 
                 repo.ui.note(_(b" %s: picking 'keep absent' action\n") % f)
                 mresult.addfile(f, *bids[mergestatemod.ACTION_KEEP_ABSENT][0])
                 continue
+            # If keep new is an option, let's just do that
+            if mergestatemod.ACTION_KEEP_NEW in bids:
+                repo.ui.note(_(b" %s: picking 'keep new' action\n") % f)
+                mresult.addfile(f, *bids[mergestatemod.ACTION_KEEP_NEW][0])
+                continue
             # If there are gets and they all agree [how could they not?], do it.
             if mergestatemod.ACTION_GET in bids:
                 ga0 = bids[mergestatemod.ACTION_GET][0]
@@ -1537,15 +1543,9 @@ 
         progress.increment(item=f)
 
     # keep (noop, just log it)
-    for f, args, msg in mresult.getactions(
-        (mergestatemod.ACTION_KEEP,), sort=True
-    ):
-        repo.ui.debug(b" %s: %s -> k\n" % (f, msg))
-        # no progress
-    for f, args, msg in mresult.getactions(
-        (mergestatemod.ACTION_KEEP_ABSENT,), sort=True
-    ):
-        repo.ui.debug(b" %s: %s -> ka\n" % (f, msg))
+    for a in mergeresult.NO_OP_ACTIONS:
+        for f, args, msg in mresult.getactions((a,), sort=True):
+            repo.ui.debug(b" %s: %s -> %s\n" % (f, msg, a))
         # no progress
 
     # directory rename, move local