Rev 1548: Merge support for pushing merged revisions. in http://people.samba.org/bzr/jelmer/bzr-svn/trunk

Jelmer Vernooij jelmer at samba.org
Mon Aug 4 17:57:14 BST 2008


At http://people.samba.org/bzr/jelmer/bzr-svn/trunk

------------------------------------------------------------
revno: 1548
revision-id: jelmer at samba.org-20080804165709-2ieavo31jeov3oqv
parent: jelmer at samba.org-20080804153730-cyn0ojl8tg2fgum3
parent: jelmer at samba.org-20080804163735-m3uxvbm321y7pj7r
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: 0.4
timestamp: Mon 2008-08-04 18:57:09 +0200
message:
  Merge support for pushing merged revisions.
modified:
  AUTHORS                        AUTHORS-20060508114718-4c90c0062645106d
  BRANCH.TODO                    branch.todo-20070721175243-w23kkak0gm2jbr8b-1
  NEWS                           news-20061231030336-h9fhq245ie0de8bs-1
  branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
  branchprops.py                 branchprops.py-20061223204623-80lvm7pjrpsgk0dd-1
  changes.py                     changes.py-20080330205801-lh92uht2ztppvdcz-1
  commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
  config.py                      config.py-20070624185721-0j8f1ly75uo4s1lk-1
  mapping.py                     mapping.py-20080128201303-6cp01phc0dmc0kiv-1
  mapping3/__init__.py           __init__.py-20080502174630-9324zh25kka98vlw-1
  remote.py                      format.py-20060406233823-b6fa009fe35dfde7
  revids.py                      revids.py-20070416220458-36vfa0730cchevp1-1
  tests/test_push.py             test_push.py-20070201165715-g2ievcdfqi33wqsy-1
  tests/test_revids.py           test_revids.py-20070516230044-d7x872cqi7xb4eow-1
    ------------------------------------------------------------
    revno: 1545.1.22
    revision-id: jelmer at samba.org-20080804163735-m3uxvbm321y7pj7r
    parent: jelmer at samba.org-20080804162324-73wmjhv74lmbzgmh
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 18:37:35 +0200
    message:
      Add configuration option for pushing merged revisions.
    modified:
      NEWS                           news-20061231030336-h9fhq245ie0de8bs-1
      config.py                      config.py-20070624185721-0j8f1ly75uo4s1lk-1
      mapping3/__init__.py           __init__.py-20080502174630-9324zh25kka98vlw-1
    ------------------------------------------------------------
    revno: 1545.1.21
    revision-id: jelmer at samba.org-20080804162324-73wmjhv74lmbzgmh
    parent: jelmer at samba.org-20080804160825-k9k3pn6ahyfxot27
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 18:23:24 +0200
    message:
      Require source repository to be passed to push only, not source branch.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
      remote.py                      format.py-20060406233823-b6fa009fe35dfde7
      tests/test_push.py             test_push.py-20070201165715-g2ievcdfqi33wqsy-1
    ------------------------------------------------------------
    revno: 1545.1.20
    revision-id: jelmer at samba.org-20080804160825-k9k3pn6ahyfxot27
    parent: jelmer at samba.org-20080804154802-1192erejvzdal0oe
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 18:08:25 +0200
    message:
      Fix tests, share more code.
    modified:
      AUTHORS                        AUTHORS-20060508114718-4c90c0062645106d
      BRANCH.TODO                    branch.todo-20070721175243-w23kkak0gm2jbr8b-1
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
      tests/test_revids.py           test_revids.py-20070516230044-d7x872cqi7xb4eow-1
    ------------------------------------------------------------
    revno: 1545.1.19
    revision-id: jelmer at samba.org-20080804154802-1192erejvzdal0oe
    parent: jelmer at samba.org-20080804154744-0nhbpqfh3y1xv3hu
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 17:48:02 +0200
    message:
      Avoid double encoding.
    modified:
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
    ------------------------------------------------------------
    revno: 1545.1.18
    revision-id: jelmer at samba.org-20080804154744-0nhbpqfh3y1xv3hu
    parent: jelmer at samba.org-20080804154727-m96k1axtcuzt805o
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 17:47:44 +0200
    message:
      Properly encode unicode strings.
    modified:
      mapping.py                     mapping.py-20080128201303-6cp01phc0dmc0kiv-1
    ------------------------------------------------------------
    revno: 1545.1.17
    revision-id: jelmer at samba.org-20080804154727-m96k1axtcuzt805o
    parent: jelmer at samba.org-20080803165708-2jyf59179jrjza2t
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Mon 2008-08-04 17:47:27 +0200
    message:
      Replace directory separators.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.16
    revision-id: jelmer at samba.org-20080803165708-2jyf59179jrjza2t
    parent: jelmer at samba.org-20080803164254-8hx3afbt3p6nhs9l
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 18:57:08 +0200
    message:
      Reduce number of revisions searched during bisect.
    modified:
      revids.py                      revids.py-20070416220458-36vfa0730cchevp1-1
    ------------------------------------------------------------
    revno: 1545.1.15
    revision-id: jelmer at samba.org-20080803164254-8hx3afbt3p6nhs9l
    parent: jelmer at samba.org-20080803164220-27pf97x2fe9duajb
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 18:42:54 +0200
    message:
      Avoid pushing revisions more than once.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.14
    revision-id: jelmer at samba.org-20080803164220-27pf97x2fe9duajb
    parent: jelmer at samba.org-20080803164148-ilobgwf4nd7lce9s
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 18:42:20 +0200
    message:
      Implement BranchingSchemeDerivedLayout.__repr__() as it's used as key in revid cache.
    modified:
      mapping3/__init__.py           __init__.py-20080502174630-9324zh25kka98vlw-1
    ------------------------------------------------------------
    revno: 1545.1.13
    revision-id: jelmer at samba.org-20080803164148-ilobgwf4nd7lce9s
    parent: jelmer at samba.org-20080803155905-dk9t1da9cjr4aviy
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 18:41:48 +0200
    message:
      Cache revid results properly.
    modified:
      revids.py                      revids.py-20070416220458-36vfa0730cchevp1-1
    ------------------------------------------------------------
    revno: 1545.1.12
    revision-id: jelmer at samba.org-20080803155905-dk9t1da9cjr4aviy
    parent: jelmer at samba.org-20080803151349-l2told14238rupq6
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 17:59:05 +0200
    message:
      Fix caching.
    modified:
      changes.py                     changes.py-20080330205801-lh92uht2ztppvdcz-1
      revids.py                      revids.py-20070416220458-36vfa0730cchevp1-1
    ------------------------------------------------------------
    revno: 1545.1.11
    revision-id: jelmer at samba.org-20080803151349-l2told14238rupq6
    parent: jelmer at samba.org-20080803151220-76vjsflj3utgjdg6
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 17:13:49 +0200
    message:
      Extra paranoia checks.
    modified:
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
    ------------------------------------------------------------
    revno: 1545.1.10
    revision-id: jelmer at samba.org-20080803151220-76vjsflj3utgjdg6
    parent: jelmer at samba.org-20080803151202-k2p9frleszlhz94a
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 17:12:20 +0200
    message:
      Encode branch nick.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.9
    revision-id: jelmer at samba.org-20080803151202-k2p9frleszlhz94a
    parent: jelmer at samba.org-20080803055344-7k7n1t6sdudph13f
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 17:12:02 +0200
    message:
      Fix double encoding.
    modified:
      branchprops.py                 branchprops.py-20061223204623-80lvm7pjrpsgk0dd-1
    ------------------------------------------------------------
    revno: 1545.1.8
    revision-id: jelmer at samba.org-20080803055344-7k7n1t6sdudph13f
    parent: jelmer at samba.org-20080803054823-qumf91ve5o10zfpf
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 07:53:44 +0200
    message:
      Make sure mainline is never interrupted.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.7
    revision-id: jelmer at samba.org-20080803054823-qumf91ve5o10zfpf
    parent: jelmer at samba.org-20080803053609-2tu1pbbnp17b5tq3
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 07:48:23 +0200
    message:
      Deal with ghosts.
    modified:
      BRANCH.TODO                    branch.todo-20070721175243-w23kkak0gm2jbr8b-1
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.6
    revision-id: jelmer at samba.org-20080803053609-2tu1pbbnp17b5tq3
    parent: jelmer at samba.org-20080803053603-g4z6lccyt5751fe5
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 07:36:09 +0200
    message:
      Update TODO.
    modified:
      BRANCH.TODO                    branch.todo-20070721175243-w23kkak0gm2jbr8b-1
    ------------------------------------------------------------
    revno: 1545.1.5
    revision-id: jelmer at samba.org-20080803053603-g4z6lccyt5751fe5
    parent: jelmer at samba.org-20080803053531-8bnik0d6ea3kwshh
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 07:36:03 +0200
    message:
      Support octopus merges.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.4
    revision-id: jelmer at samba.org-20080803053531-8bnik0d6ea3kwshh
    parent: jelmer at samba.org-20080803045431-772f2aatnzawcblt
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 07:35:31 +0200
    message:
      Add extra asserts.
    modified:
      revids.py                      revids.py-20070416220458-36vfa0730cchevp1-1
    ------------------------------------------------------------
    revno: 1545.1.3
    revision-id: jelmer at samba.org-20080803045431-772f2aatnzawcblt
    parent: jelmer at samba.org-20080803045420-629aphb47gxubij2
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 06:54:31 +0200
    message:
      Fix property name of branch nick.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
    ------------------------------------------------------------
    revno: 1545.1.2
    revision-id: jelmer at samba.org-20080803045420-629aphb47gxubij2
    parent: jelmer at samba.org-20080803043852-tjf1qt7q86pe2t4m
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 06:54:20 +0200
    message:
      Implement ImaginaryBranch._get_append_revisions_only
    modified:
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
    ------------------------------------------------------------
    revno: 1545.1.1
    revision-id: jelmer at samba.org-20080803043852-tjf1qt7q86pe2t4m
    parent: jelmer at samba.org-20080803002744-ldwouhqqbftwz5g8
    committer: Jelmer Vernooij <jelmer at samba.org>
    branch nick: pushmerged
    timestamp: Sun 2008-08-03 06:38:52 +0200
    message:
      Merge initial support for pushing merged revisions.
    modified:
      branch.py                      svnbranch.py-20051017135706-11c749eb0dab04a7
      commit.py                      commit.py-20060607190346-qvq128wgfubhhgm2-1
      mapping3/__init__.py           __init__.py-20080502174630-9324zh25kka98vlw-1
      mapping3/scheme.py             scheme.py-20060516195850-95181aae6b272f9e
=== modified file 'AUTHORS'
--- a/AUTHORS	2008-07-30 10:42:53 +0000
+++ b/AUTHORS	2008-08-04 16:08:25 +0000
@@ -13,6 +13,7 @@
 Jerry Carter
 Chandler Carruth
 Robert Collins
+Mattias Eriksson
 David Foerster
 Mirko Friedenhagen
 Martin von Gagern

=== modified file 'BRANCH.TODO'
--- a/BRANCH.TODO	2008-07-04 03:32:12 +0000
+++ b/BRANCH.TODO	2008-08-04 16:08:25 +0000
@@ -1,5 +1,8 @@
+pushmerge:
+ - make pushmerge option in repository configuration
+ - create branches/ dir automatically
+
 before 0.4.10:
- - regression in http hack?
  - use parents cache more agressively
  - move some config options from RepositoryConfig to BranchConfig
  - use -1 to mean youngest revnum

=== modified file 'NEWS'
--- a/NEWS	2008-08-03 00:02:00 +0000
+++ b/NEWS	2008-08-04 16:37:35 +0000
@@ -51,6 +51,9 @@
    * Support bzr sign-my-commits. (Requires revision properties in the 
 	 Subversion repository to be mutable)
 
+   * Support pushing merged revisions. To enable, set 
+     ``push_merged_revisions = True'' in the repository config. (#158883)
+
   BUG FIXES
 
    * Now uses absolute imports and no longer adds plugin directory to the 

=== modified file 'branch.py'
--- a/branch.py	2008-08-02 23:41:33 +0000
+++ b/branch.py	2008-08-04 16:23:24 +0000
@@ -30,7 +30,7 @@
 from bzrlib.plugins.svn import core, wc
 from bzrlib.plugins.svn.auth import create_auth_baton
 from bzrlib.plugins.svn.client import Client, get_config
-from bzrlib.plugins.svn.commit import push
+from bzrlib.plugins.svn.commit import push, push_ancestors
 from bzrlib.plugins.svn.config import BranchConfig
 from bzrlib.plugins.svn.core import SubversionException
 from bzrlib.plugins.svn.errors import NotSvnBranchPath, ERR_FS_NO_SUCH_REVISION
@@ -335,7 +335,7 @@
         """See Branch.set_revision_history()."""
         if rev_history == [] or not self.repository.has_revision(rev_history[-1]):
             raise NotImplementedError("set_revision_history can't add ghosts")
-        push(self, self, rev_history[-1])
+        push(self, self.repository, rev_history[-1])
         self._clear_cached_state()
 
     def set_last_revision_info(self, revno, revid):
@@ -506,12 +506,18 @@
         self._push_missing_revisions(other, todo)
 
     def _push_missing_revisions(self, other, todo):
+        push_merged = self.layout.push_merged_revisions(self.project)
+        if push_merged:
+            graph = other.repository.get_graph()
         pb = ui.ui_factory.nested_progress_bar()
         try:
             for revid in todo:
                 pb.update("pushing revisions", todo.index(revid), 
                           len(todo))
-                push(self, other, revid)
+                if push_merged:
+                    parent_revids = graph.get_parent_map([revid])[revid]
+                    push_ancestors(self.repository, other.repository, self.layout, self.project, parent_revids, graph)
+                push(self, other.repository, revid)
                 self._clear_cached_state()
         finally:
             pb.finished()

=== modified file 'branchprops.py'
--- a/branchprops.py	2008-07-21 20:46:23 +0000
+++ b/branchprops.py	2008-08-03 15:12:02 +0000
@@ -67,8 +67,8 @@
         if prev_path is None and prev_revnum == -1:
             previous = {}
         else:
-            previous = self.get_properties(prev_path.encode("utf-8"), 
-                                           prev_revnum)
+            assert isinstance(prev_path, str)
+            previous = self.get_properties(prev_path, prev_revnum)
         ret = {}
         for key, val in current.items():
             if previous.get(key) != val:

=== modified file 'changes.py'
--- a/changes.py	2008-03-30 20:59:01 +0000
+++ b/changes.py	2008-08-03 15:59:05 +0000
@@ -42,7 +42,8 @@
         if paths[branch_path][1] is None: 
             return None # Was added here
         revnum = paths[branch_path][2]
-        branch_path = paths[branch_path][1].encode("utf-8")
+        assert isinstance(paths[branch_path][1], str)
+        branch_path = paths[branch_path][1]
         return (branch_path, revnum)
     
     # Make sure we get the right location for the next time if 

=== modified file 'commit.py'
--- a/commit.py	2008-08-02 21:53:02 +0000
+++ b/commit.py	2008-08-04 16:23:24 +0000
@@ -21,7 +21,7 @@
                            UnrelatedBranches, AppendRevisionsOnlyViolation,
                            NoSuchRevision)
 from bzrlib.inventory import Inventory
-from bzrlib.repository import RootCommitBuilder, InterRepository
+from bzrlib.repository import RootCommitBuilder, InterRepository, Repository
 from bzrlib.revision import NULL_REVISION, ensure_null
 from bzrlib.trace import mutter, warning
 
@@ -65,6 +65,7 @@
     for i in range(len(bp_parts), 0, -1):
         current = bp_parts[:i]
         path = "/".join(current).strip("/")
+        assert isinstance(path, str)
         if transport.check_path(path, base_rev) == core.NODE_DIR:
             return current
     return []
@@ -438,7 +439,9 @@
             """
             self.revision_metadata = args
         
-        bp_parts = self.branch.get_branch_path().split("/")
+        bp = self.branch.get_branch_path()
+        assert isinstance(bp, str), "%r" % bp
+        bp_parts = bp.split("/")
         repository_latest_revnum = self.repository.get_latest_revnum()
         lock = self.repository.transport.lock_write(".")
         set_revprops = self._config.get_set_revprops()
@@ -526,8 +529,7 @@
                 for prop, value in self._svnprops.items():
                     if not properties.is_valid_property_name(prop):
                         warning("Setting property %r with invalid characters in name", prop)
-                    if value is not None:
-                        value = value.encode('utf-8')
+                    assert isinstance(value, str)
                     branch_editors[-1].change_prop(prop, value)
                     self.mutter("Setting root file property %r -> %r", prop, value)
 
@@ -647,10 +649,10 @@
 
     :param target_repository: Repository to push to
     :param target_branch_path: Path to create new branch at
-    :param source: Branch to pull the revision from
+    :param source: Source repository
     """
-    assert isinstance(source, Branch)
-    revhistory = list(source.repository.iter_reverse_revision_history(stop_revision))
+    assert isinstance(source, Repository)
+    revhistory = list(source.iter_reverse_revision_history(stop_revision))
     history = list(revhistory)
     history.reverse()
     start_revid_parent = NULL_REVISION
@@ -671,6 +673,9 @@
             self.repository = repository
             self._revision_history = None
 
+        def _get_append_revisions_only(self):
+            return False
+
         def get_config(self):
             """See Branch.get_config()."""
             return self.repository.get_config()
@@ -730,7 +735,7 @@
             for revid in todo:
                 pb.update("pushing revisions", todo.index(revid), 
                           len(todo))
-                revid_map[revid] = push(target, source, revid, 
+                revid_map[revid] = push(target, source.repository, revid, 
                                         push_metadata=False)
                 source.repository.fetch(target.repository, 
                                         revision_id=revid_map[revid])
@@ -776,18 +781,18 @@
     return revid
 
 
-def push(target, source, revision_id, push_metadata=True):
+def push(target, source_repo, revision_id, push_metadata=True):
     """Push a revision into Subversion.
 
     This will do a new commit in the target branch.
 
     :param target: Branch to push to
-    :param source: Branch to pull the revision from
+    :param source_repo: Branch to pull the revision from
     :param revision_id: Revision id of the revision to push
     :return: revision id of revision that was pushed
     """
-    assert isinstance(source, Branch)
-    rev = source.repository.get_revision(revision_id)
+    assert isinstance(source_repo, Repository)
+    rev = source_repo.get_revision(revision_id)
     mutter('pushing %r (%r)', revision_id, rev.parent_ids)
 
     # revision on top of which to commit
@@ -799,13 +804,13 @@
     else:
         base_revid = target.last_revision()
 
-    source.lock_read()
+    source_repo.lock_read()
     try:
         revid = push_revision_tree(target, target.get_config(), 
-                                   source.repository, base_revid, revision_id, 
+                                   source_repo, base_revid, revision_id, 
                                    rev, push_metadata=push_metadata)
     finally:
-        source.unlock()
+        source_repo.unlock()
 
     assert revid == revision_id or not push_metadata
 
@@ -854,6 +859,8 @@
                 return
             mutter("pushing %r into svn", todo)
             target_branch = None
+            layout = self.target.get_layout()
+            graph = self.target.get_graph()
             for revision_id in todo:
                 if pb is not None:
                     pb.update("pushing revisions", todo.index(revision_id), len(todo))
@@ -869,7 +876,11 @@
                 if target_branch.get_branch_path() != bp:
                     target_branch.set_branch_path(bp)
 
-                push_revision_tree(target_branch, target_branch.get_config(), self.source, 
+                if layout.push_merged_revisions(target_branch.project) and len(rev.parent_ids) > 1:
+                    push_ancestors(self.target, self.source, layout, "", rev.parent_ids, graph)
+
+                target_config = target_branch.get_config()
+                push_revision_tree(target_branch, target_config, self.source, 
                                    parent_revid, revision_id, rev)
         finally:
             self.source.unlock()
@@ -883,3 +894,18 @@
     def is_compatible(source, target):
         """Be compatible with SvnRepository."""
         return isinstance(target, SvnRepository)
+
+
+def push_ancestors(target_repo, source_repo, layout, project, parent_revids, graph):
+    for parent_revid in parent_revids[1:]:
+        if target_repo.has_revision(parent_revid):
+            continue
+        # Push merged revisions
+        unique_ancestors = graph.find_unique_ancestors(parent_revid, [parent_revids[0]])
+        for x in graph.iter_topo_order(unique_ancestors):
+            if target_repo.has_revision(x):
+                continue
+            rev = source_repo.get_revision(x)
+            nick = (rev.properties.get('branch-nick') or "merged").encode("utf-8").replace("/","_")
+            rhs_branch_path = layout.get_branch_path(nick, project)
+            push_new(target_repo, rhs_branch_path, source_repo, x)

=== modified file 'config.py'
--- a/config.py	2008-07-08 23:28:17 +0000
+++ b/config.py	2008-08-04 16:37:35 +0000
@@ -173,6 +173,13 @@
             return set()
         return set(val.split(";"))
 
+    def get_push_merged_revisions(self):
+        """Check whether merged revisions should be pushed."""
+        try:
+            return self._get_parser().get_bool(self.uuid, "push_merged_revisions")
+        except KeyError:
+            return None
+
     def add_location(self, location):
         """Add a location for this repository.
 

=== modified file 'mapping.py'
--- a/mapping.py	2008-07-23 19:35:24 +0000
+++ b/mapping.py	2008-08-04 15:47:44 +0000
@@ -219,11 +219,12 @@
     if timestamp is not None:
         text += "timestamp: %s\n" % format_highres_date(timestamp, timezone) 
     if committer is not None:
-        text += "committer: %s\n" % committer
+        text += "committer: %s\n" % committer.encode("utf-8")
     if revprops is not None and revprops != {}:
         text += "properties: \n"
         for k, v in sorted(revprops.items()):
-            text += "\t%s: %s\n" % (k, v)
+            text += "\t%s: %s\n" % (k.encode("utf-8"), v.encode("utf-8"))
+    assert isinstance(text, str)
     return text
 
 

=== modified file 'mapping3/__init__.py'
--- a/mapping3/__init__.py	2008-08-03 14:54:12 +0000
+++ b/mapping3/__init__.py	2008-08-04 16:57:09 +0000
@@ -115,6 +115,9 @@
     def get_branch_path(self, name, project=""):
         return self.scheme.get_branch_path(name, project)
 
+    def get_branch_path(self, name, project=""):
+        return self.scheme.get_branch_path(name, project)
+
     def is_branch_parent(self, path):
         # Na, na, na...
         return self.scheme.is_branch_parent(path)
@@ -126,10 +129,13 @@
     def push_merged_revisions(self, project=""):
         try:
             self.scheme.get_branch_path("somebranch")
-            return True
+            return self.repository.get_config().get_push_merged_revisions()
         except NotImplementedError:
             return False
 
+    def __repr__(self):
+        return "%s(%s)" % (self.__class__.__name__, repr(self.scheme))
+
 
 def get_stored_scheme(repository):
     """Retrieve the stored branching scheme, either in the repository 

=== modified file 'remote.py'
--- a/remote.py	2008-07-08 23:28:17 +0000
+++ b/remote.py	2008-08-04 16:23:24 +0000
@@ -139,7 +139,7 @@
                 if repos.transport.check_path(target_branch_path,
                     repos.get_latest_revnum()) != core.NODE_NONE:
                     raise AlreadyBranchError(full_branch_url)
-                push_new(repos, target_branch_path, source, stop_revision)
+                push_new(repos, target_branch_path, source.repository, stop_revision)
             finally:
                 repos.unlock()
             branch = self.open_branch()

=== modified file 'revids.py'
--- a/revids.py	2008-07-23 00:37:07 +0000
+++ b/revids.py	2008-08-03 16:57:08 +0000
@@ -64,7 +64,8 @@
 
         for entry_revid, branch, revno, mapping in self.discover_revids(layout, 0, self.repos.get_latest_revnum()):
             if revid == entry_revid:
-                return self.bisect_revid_revnum(revid, branch, 0, revno)
+                (bp, revnum, scheme) = self.bisect_revid_revnum(revid, branch, 0, revno)
+                return (bp, revnum, BzrSvnMappingv3FileProps(scheme))
         raise NoSuchRevision(self, revid)
 
     def discover_revids(self, layout, from_revnum, to_revnum):
@@ -93,6 +94,15 @@
                 yield (entry_revid, branch, revno, BzrSvnMappingv3FileProps(BranchingScheme.find_scheme(scheme)))
 
     def bisect_revid_revnum(self, revid, branch_path, min_revnum, max_revnum):
+        """Find out what the actual revnum was that corresponds to a revid.
+
+        :param revid: Revision id to search for
+        :param branch_path: Branch path at which to start searching
+        :param min_revnum: Last revnum to check
+        :param max_revnum: First revnum to check
+        :return: Tuple with actual branchpath, revnum and scheme
+        """
+        assert min_revnum <= max_revnum
         # Find the branch property between min_revnum and max_revnum that 
         # added revid
         for revmeta in self.repos.iter_reverse_branch_changes(branch_path, max_revnum, min_revnum):
@@ -110,7 +120,7 @@
                     scheme = BranchingScheme.find_scheme(propname[len(SVN_PROP_BZR_REVISION_ID):])
                     assert (scheme.is_tag(revmeta.branch_path) or 
                             scheme.is_branch(revmeta.branch_path))
-                    return (revmeta.branch_path, revmeta.revnum, BzrSvnMappingv3FileProps(scheme))
+                    return (revmeta.branch_path, revmeta.revnum, scheme)
 
         raise InvalidBzrSvnRevision(revid)
 
@@ -119,6 +129,7 @@
     def __init__(self, actual, cachedb=None):
         self.cache = RevisionIdMapCache(cachedb)
         self.actual = actual
+        self.revid_seen = set()
 
     def get_revision_id(self, revnum, path, mapping, changed_fileprops, revprops):
         # Look in the cache to see if it already has a revision id
@@ -159,34 +170,39 @@
             assert isinstance(branch_path, str)
             assert isinstance(scheme, str)
             # Entry already complete?
+            assert min_revnum <= max_revnum
             if min_revnum == max_revnum:
                 return (branch_path, min_revnum, BzrSvnMappingv3FileProps(get_scheme(scheme)))
         except NoSuchRevision, e:
             last_revnum = self.actual.repos.get_latest_revnum()
-            if (last_revnum <= self.cache.last_revnum_checked(str(layout))):
+            last_checked = self.cache.last_revnum_checked(repr(layout))
+            if (last_revnum <= last_checked):
                 # All revision ids in this repository for the current 
                 # layout have already been discovered. No need to 
                 # check again.
                 raise e
             found = False
-            revid_seen = set()
-            for entry_revid, branch, revno, mapping in self.actual.discover_revids(layout, self.cache.last_revnum_checked(str(layout)), last_revnum):
+            for entry_revid, branch, revno, mapping in self.actual.discover_revids(layout, last_checked, last_revnum):
                 if entry_revid == revid:
                     found = True
-                if entry_revid not in revid_seen:
-                    self.cache.insert_revid(entry_revid, branch, 0, revno, str(mapping.scheme))
-                    revid_seen.add(entry_revid)
+                if entry_revid not in self.revid_seen:
+                    self.cache.insert_revid(entry_revid, branch, last_checked, revno, str(mapping.scheme))
+                    self.revid_seen.add(entry_revid)
                 
             # We've added all the revision ids for this layout in the repository,
             # so no need to check again unless new revisions got added
-            self.cache.set_last_revnum_checked(str(layout), last_revnum)
+            self.cache.set_last_revnum_checked(repr(layout), last_revnum)
             if not found:
                 raise e
             (branch_path, min_revnum, max_revnum, scheme) = self.cache.lookup_revid(revid)
+            assert min_revnum <= max_revnum
             assert isinstance(branch_path, str)
 
-        return self.actual.bisect_revid_revnum(revid, branch_path, min_revnum,
+        (branch_path, revnum, scheme) = self.actual.bisect_revid_revnum(revid, branch_path, min_revnum,
                                                max_revnum)
+        self.cache.insert_revid(revid, branch_path, revnum, revnum, str(scheme))
+        return (branch_path, revnum, BzrSvnMappingv3FileProps(scheme))
+
 
 
 class RevisionIdMapCache(CacheTable):
@@ -244,7 +260,11 @@
             "select path, min_revnum, max_revnum, scheme from revmap where revid=?", (revid,)).fetchone()
         if ret is None:
             raise NoSuchRevision(self, revid)
-        return (ret[0].encode("utf-8"), int(ret[1]), int(ret[2]), ret[3].encode("utf-8"))
+        (path, min_revnum, max_revnum, scheme) = (ret[0].encode("utf-8"), int(ret[1]), int(ret[2]), ret[3].encode("utf-8"))
+        if min_revnum > max_revnum:
+            return (path, max_revnum, min_revnum, scheme)
+        else:
+            return (path, min_revnum, max_revnum, scheme)
 
     def lookup_branch_revnum(self, revnum, path, scheme):
         """Lookup a revision by revision number, branch path and branching scheme.
@@ -257,7 +277,7 @@
         assert isinstance(path, str)
         assert isinstance(scheme, str)
         row = self.cachedb.execute(
-                "select revid from revmap where max_revnum = ? and min_revnum=? and path=? and scheme=?", (revnum, revnum, path, scheme)).fetchone()
+                "select revid from revmap where max_revnum=? and min_revnum=? and path=? and scheme=?", (revnum, revnum, path, scheme)).fetchone()
         if row is not None:
             ret = str(row[0])
         else:
@@ -281,10 +301,16 @@
         assert isinstance(scheme, str)
         assert isinstance(branch, str)
         assert isinstance(min_revnum, int) and isinstance(max_revnum, int)
+        assert min_revnum <= max_revnum
         self.mutter("insert revid %r:%r-%r -> %r", branch, min_revnum, max_revnum, revid)
-        cursor = self.cachedb.execute(
-            "update revmap set min_revnum = MAX(min_revnum,?), max_revnum = MIN(max_revnum, ?) WHERE revid=? AND path=? AND scheme=?",
-            (min_revnum, max_revnum, revid, branch, scheme))
+        if min_revnum == max_revnum:
+            cursor = self.cachedb.execute(
+                "update revmap set min_revnum = ?, max_revnum = ? WHERE revid=? AND path=? AND scheme=?",
+                (min_revnum, max_revnum, revid, branch, scheme))
+        else:
+            cursor = self.cachedb.execute(
+                "update revmap set min_revnum = MAX(min_revnum,?), max_revnum = MIN(max_revnum, ?) WHERE revid=? AND path=? AND scheme=?",
+                (min_revnum, max_revnum, revid, branch, scheme))
         if cursor.rowcount == 0:
             self.cachedb.execute(
                 "insert into revmap (revid,path,min_revnum,max_revnum,scheme) VALUES (?,?,?,?,?)",

=== modified file 'tests/test_push.py'
--- a/tests/test_push.py	2008-08-02 21:53:02 +0000
+++ b/tests/test_push.py	2008-08-04 16:23:24 +0000
@@ -437,12 +437,12 @@
         self.build_tree({'mybranch/foo': 'bladata'})
         wt = self.bzrdir.open_workingtree()
         revid = wt.commit(message="Commit from Bzr")
-        push(Branch.open("%s/trunk" % self.repos_url), wt.branch, 
+        push(Branch.open("%s/trunk" % self.repos_url), wt.branch.repository, 
              wt.branch.revision_history()[-2])
         mutter('log %r' % self.client_log("%s/trunk" % self.repos_url, 0, 4)[4][0])
         self.assertEquals('M',
             self.client_log("%s/trunk" % self.repos_url, 0, 4)[4][0]['/trunk'][0])
-        push(Branch.open("%s/trunk" % self.repos_url), wt.branch, wt.branch.last_revision())
+        push(Branch.open("%s/trunk" % self.repos_url), wt.branch.repository, wt.branch.last_revision())
         mutter('log %r' % self.client_log("%s/trunk" % self.repos_url, 0, 5)[5][0])
         self.assertEquals("/branches/mybranch", 
             self.client_log("%s/trunk" % self.repos_url, 0, 5)[5][0]['/trunk'][1])

=== modified file 'tests/test_revids.py'
--- a/tests/test_revids.py	2008-06-04 15:20:12 +0000
+++ b/tests/test_revids.py	2008-08-04 16:08:25 +0000
@@ -54,6 +54,6 @@
 
     def test_lookup_branch_incomplete(self):
         revidmap = RevisionIdMapCache()
-        revidmap.insert_revid("bla", "mypath", 200, 42, "brainslug")
+        revidmap.insert_revid("bla", "mypath", 42, 200, "brainslug")
         self.assertEquals(None, 
                 revidmap.lookup_branch_revnum(42, "mypath", "brainslug"))




More information about the bazaar-commits mailing list