Rev 3016: Migrate switch command into the core (Ian Clatworthy) in file:///home/pqm/archives/thelove/bzr/%2Btrunk/

Canonical.com Patch Queue Manager pqm at pqm.ubuntu.com
Fri Nov 23 04:39:57 GMT 2007


At file:///home/pqm/archives/thelove/bzr/%2Btrunk/

------------------------------------------------------------
revno: 3016
revision-id:pqm at pqm.ubuntu.com-20071123043953-lv68pawzrpa4s9t9
parent: pqm at pqm.ubuntu.com-20071122234103-fn117zncqrqv39me
parent: ian.clatworthy at internode.on.net-20071123035952-26dxxzpf5vc1lxqk
committer: Canonical.com Patch Queue Manager <pqm at pqm.ubuntu.com>
branch nick: +trunk
timestamp: Fri 2007-11-23 04:39:53 +0000
message:
  Migrate switch command into the core (Ian Clatworthy)
added:
  bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
  bzrlib/tests/blackbox/test_switch.py test_switch.py-20071122111948-0c5en6uz92bwl76h-1
  bzrlib/tests/test_switch.py    test_switch.py-20071116011000-v5lnw7d2wkng9eux-2
modified:
  NEWS                           NEWS-20050323055033-4e00b5db738777ff
  bzrlib/builtins.py             builtins.py-20050830033751-fc01482b9ca23183
  bzrlib/revision.py             revision.py-20050309040759-e77802c08f3999d5
  bzrlib/tests/__init__.py       selftest.py-20050531073622-8d0e3c8845c97a64
  bzrlib/tests/blackbox/__init__.py __init__.py-20051128053524-eba30d8255e08dc3
    ------------------------------------------------------------
    revno: 3015.1.2
    revision-id:ian.clatworthy at internode.on.net-20071123035952-26dxxzpf5vc1lxqk
    parent: ian.clatworthy at internode.on.net-20071123001902-h4w2nqsli32tl56w
    parent: ian.clatworthy at internode.on.net-20071123033317-x2msj6t0nj4mbqxl
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: ianc-integration
    timestamp: Fri 2007-11-23 13:59:52 +1000
    message:
      Migrate switch command into the core (Ian Clatworthy)
    modified:
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
        ------------------------------------------------------------
        revno: 2999.1.5
        revision-id:ian.clatworthy at internode.on.net-20071123033317-x2msj6t0nj4mbqxl
        parent: ian.clatworthy at internode.on.net-20071122112100-15wtitw0o1kwckit
        committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
        branch nick: bzr.switch-into-core
        timestamp: Fri 2007-11-23 13:33:17 +1000
        message:
          make switch.py unix file format, not dos
        modified:
          bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
    ------------------------------------------------------------
    revno: 3015.1.1
    revision-id:ian.clatworthy at internode.on.net-20071123001902-h4w2nqsli32tl56w
    parent: pqm at pqm.ubuntu.com-20071122234103-fn117zncqrqv39me
    parent: ian.clatworthy at internode.on.net-20071122112100-15wtitw0o1kwckit
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: ianc-integration
    timestamp: Fri 2007-11-23 10:19:02 +1000
    message:
      Migrate switch command into the core (Ian Clatworthy)
    added:
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
      bzrlib/tests/blackbox/test_switch.py test_switch.py-20071122111948-0c5en6uz92bwl76h-1
      bzrlib/tests/test_switch.py    test_switch.py-20071116011000-v5lnw7d2wkng9eux-2
    modified:
      NEWS                           NEWS-20050323055033-4e00b5db738777ff
      bzrlib/builtins.py             builtins.py-20050830033751-fc01482b9ca23183
      bzrlib/revision.py             revision.py-20050309040759-e77802c08f3999d5
      bzrlib/tests/__init__.py       selftest.py-20050531073622-8d0e3c8845c97a64
      bzrlib/tests/blackbox/__init__.py __init__.py-20051128053524-eba30d8255e08dc3
    ------------------------------------------------------------
    revno: 2999.1.4
    revision-id:ian.clatworthy at internode.on.net-20071122112100-15wtitw0o1kwckit
    parent: ian.clatworthy at internode.on.net-20071122043128-bjlhladklqlmfo4d
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: bzr.switch-into-core
    timestamp: Thu 2007-11-22 21:21:00 +1000
    message:
      more review tweaks including commit of blackbox tests
    added:
      bzrlib/tests/blackbox/test_switch.py test_switch.py-20071122111948-0c5en6uz92bwl76h-1
    modified:
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
    ------------------------------------------------------------
    revno: 2999.1.3
    revision-id:ian.clatworthy at internode.on.net-20071122043128-bjlhladklqlmfo4d
    parent: ian.clatworthy at internode.on.net-20071121151044-pnn0r0kwttjvzlfb
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: bzr.switch-into-core
    timestamp: Thu 2007-11-22 14:31:28 +1000
    message:
      fix pending merge detection and test
    modified:
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
      bzrlib/tests/test_switch.py    test_switch.py-20071116011000-v5lnw7d2wkng9eux-2
    ------------------------------------------------------------
    revno: 2999.1.2
    revision-id:ian.clatworthy at internode.on.net-20071121151044-pnn0r0kwttjvzlfb
    parent: ian.clatworthy at internode.on.net-20071116011916-cqzuyhp8vwsmyhyo
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: bzr.switch-into-core
    timestamp: Thu 2007-11-22 01:10:44 +1000
    message:
      incorporate review feedback including basic blackbox tests
    modified:
      bzrlib/builtins.py             builtins.py-20050830033751-fc01482b9ca23183
      bzrlib/revision.py             revision.py-20050309040759-e77802c08f3999d5
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
      bzrlib/tests/blackbox/__init__.py __init__.py-20051128053524-eba30d8255e08dc3
    ------------------------------------------------------------
    revno: 2999.1.1
    revision-id:ian.clatworthy at internode.on.net-20071116011916-cqzuyhp8vwsmyhyo
    parent: pqm at pqm.ubuntu.com-20071115215612-4ovlulhfxh6dhq61
    committer: Ian Clatworthy <ian.clatworthy at internode.on.net>
    branch nick: bzr.switch-into-core
    timestamp: Fri 2007-11-16 11:19:16 +1000
    message:
      migrate switch command into the core - was in BzrTools
    added:
      bzrlib/switch.py               switch.py-20071116011000-v5lnw7d2wkng9eux-1
      bzrlib/tests/test_switch.py    test_switch.py-20071116011000-v5lnw7d2wkng9eux-2
    modified:
      NEWS                           NEWS-20050323055033-4e00b5db738777ff
      bzrlib/builtins.py             builtins.py-20050830033751-fc01482b9ca23183
      bzrlib/tests/__init__.py       selftest.py-20050531073622-8d0e3c8845c97a64
=== added file 'bzrlib/switch.py'
--- a/bzrlib/switch.py	1970-01-01 00:00:00 +0000
+++ b/bzrlib/switch.py	2007-11-23 03:33:17 +0000
@@ -0,0 +1,106 @@
+# Copyright (C) 2006, 2007 Canonical Ltd.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+# Original author: David Allouche
+
+from bzrlib import errors, merge
+from bzrlib.branch import Branch, BranchFormat, BranchReferenceFormat
+from bzrlib.bzrdir import BzrDir
+from bzrlib.trace import note
+
+
+def switch(control_dir, to_branch):
+    """Switch the branch associated with a checkout.
+
+    :param control_dir: BzrDir of the checkout to change
+    :param to_branch: branch that the checkout is to reference
+    """
+    _check_switch_branch_format(control_dir)
+    _check_pending_merges(control_dir)
+    try:
+        source_repository = control_dir.open_branch().repository
+    except errors.NotBranchError:
+        source_repository = to_branch.repository
+    _set_branch_location(control_dir, to_branch)
+    tree = control_dir.open_workingtree()
+    _update(tree, source_repository)
+
+
+def _check_switch_branch_format(control):
+    """Check that the branch format supports the switch operation.
+
+    Note: Only lightweight checkouts are currently supported.
+    This may change in the future though.
+
+    :param control: BzrDir of the branch to check
+    """
+    branch_format = BranchFormat.find_format(control)
+    format_string = branch_format.get_format_string()
+    if not format_string.startswith("Bazaar-NG Branch Reference Format "):
+        raise errors.BzrCommandError(
+            'The switch command can only be used on a lightweight checkout.\n'
+            'Expected branch reference, found %s at %s' % (
+            format_string.strip(), control.root_transport.base))
+    if not format_string == BranchReferenceFormat().get_format_string():
+        raise errors.BzrCommandError(
+            'Unsupported: %r' % (format_string.strip(),))        
+
+
+def _check_pending_merges(control):
+    """Check that there are no outstanding pending merges before switching.
+
+    :param control: BzrDir of the branch to check
+    """
+    try:
+        tree = control.open_workingtree()
+    except errors.NotBranchError:
+        # old branch is gone
+        return
+    # XXX: Should the tree be locked for get_parent_ids?
+    existing_pending_merges = tree.get_parent_ids()[1:]
+    if len(existing_pending_merges) > 0:
+        raise errors.BzrCommandError('Pending merges must be '
+            'committed or reverted before using switch.')
+
+
+def _set_branch_location(control, to_branch):
+    """Set location value of a branch reference.
+
+    :param control: BzrDir of the checkout to change
+    :param to_branch: branch that the checkout is to reference
+    """
+    transport = control.get_branch_transport(None)
+    location = transport.put_bytes('location', to_branch.base)
+
+
+def _update(tree, source_repository):
+    """Update a working tree to the latest revision of its branch.
+
+    :param tree: the working tree
+    :param source_repository: repository holding the revisions
+    """
+    tree.lock_tree_write()
+    try:
+        to_branch = tree.branch
+        if tree.last_revision() == to_branch.last_revision():
+            note("Tree is up to date at revision %d.", to_branch.revno())
+            return
+        base_tree = source_repository.revision_tree(tree.last_revision())
+        merge.Merge3Merger(tree, tree, base_tree, to_branch.basis_tree())
+        tree.set_last_revision(to_branch.last_revision())
+        note('Updated to revision %d.' % to_branch.revno())
+    finally:
+        tree.unlock()

=== added file 'bzrlib/tests/blackbox/test_switch.py'
--- a/bzrlib/tests/blackbox/test_switch.py	1970-01-01 00:00:00 +0000
+++ b/bzrlib/tests/blackbox/test_switch.py	2007-11-22 11:21:00 +0000
@@ -0,0 +1,50 @@
+# Copyright (C) 2007 Canonical Ltd
+# -*- coding: utf-8 -*-
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+
+"""Tests for the switch command of bzr."""
+
+import os
+
+from bzrlib.tests.blackbox import ExternalBase
+
+
+class TestSwitch(ExternalBase):
+
+    def test_switch_up_to_date_light_checkout(self):
+        self.make_branch_and_tree('branch')
+        self.run_bzr('branch branch branch2')
+        self.run_bzr('checkout --lightweight branch checkout')
+        os.chdir('checkout')
+        out, err = self.run_bzr('switch ../branch2')
+        self.assertContainsRe(err, 'Tree is up to date at revision 0.\n')
+        self.assertContainsRe(err, 'Switched to branch: .*/branch2.\n')
+        self.assertEqual('', out)
+
+    def test_switch_out_of_date_light_checkout(self):
+        self.make_branch_and_tree('branch')
+        self.run_bzr('branch branch branch2')
+        self.build_tree(['branch2/file'])
+        self.run_bzr('add branch2/file')
+        self.run_bzr('commit -m add-file branch2')
+        self.run_bzr('checkout --lightweight branch checkout')
+        os.chdir('checkout')
+        out, err = self.run_bzr('switch ../branch2')
+        #self.assertContainsRe(err, '\+N  file')
+        self.assertContainsRe(err, 'Updated to revision 1.\n')
+        self.assertContainsRe(err, 'Switched to branch: .*/branch2.\n')
+        self.assertEqual('', out)

=== added file 'bzrlib/tests/test_switch.py'
--- a/bzrlib/tests/test_switch.py	1970-01-01 00:00:00 +0000
+++ b/bzrlib/tests/test_switch.py	2007-11-22 04:31:28 +0000
@@ -0,0 +1,94 @@
+# Copyright (C) 2007 Canonical Ltd
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+"""Tests for bzrlib.switch."""
+
+
+import os
+
+from bzrlib import branch, errors, switch, tests
+
+
+class TestSwitch(tests.TestCaseWithTransport):
+
+    def _setup_tree(self):
+        tree = self.make_branch_and_tree('branch-1')
+        self.build_tree(['branch-1/file-1'])
+        tree.add('file-1')
+        tree.commit('rev1')
+        return tree
+
+    def test_switch_updates(self):
+        """Test switch updates tree and keeps uncommitted changes."""
+        tree = self._setup_tree()
+        to_branch = tree.bzrdir.sprout('branch-2').open_branch()
+        self.build_tree(['branch-1/file-2'])
+        tree.add('file-2')
+        tree.remove('file-1')
+        tree.commit('rev2')
+        checkout = tree.branch.create_checkout('checkout', lightweight=True)
+        self.build_tree(['checkout/file-3'])
+        checkout.add('file-3')
+        self.failIfExists('checkout/file-1')
+        self.failUnlessExists('checkout/file-2')
+        switch.switch(checkout.bzrdir, to_branch)
+        self.failUnlessExists('checkout/file-1')
+        self.failIfExists('checkout/file-2')
+        self.failUnlessExists('checkout/file-3')
+
+    def test_switch_after_branch_moved(self):
+        """Test switch after the branch is moved."""
+        tree = self._setup_tree()
+        checkout = tree.branch.create_checkout('checkout', lightweight=True)
+        self.build_tree(['branch-1/file-2'])
+        tree.add('file-2')
+        tree.remove('file-1')
+        tree.commit('rev2')
+        os.rename('branch-1', 'branch-2')
+        to_branch = branch.Branch.open('branch-2')
+        self.build_tree(['checkout/file-3'])
+        checkout.add('file-3')
+        switch.switch(checkout.bzrdir, to_branch)
+        self.failIfExists('checkout/file-1')
+        self.failUnlessExists('checkout/file-2')
+        self.failUnlessExists('checkout/file-3')
+
+    def test_switch_on_heavy_checkout(self):
+        """Test graceful failure on heavyweight checkouts."""
+        tree = self._setup_tree()
+        checkout = tree.branch.create_checkout('checkout-1', lightweight=False)
+        branch2 = self.make_branch('branch-2')
+        err = self.assertRaises(errors.BzrCommandError,
+            switch.switch, checkout.bzrdir, branch2)
+        self.assertContainsRe(str(err),
+            "The switch command can only be used on a lightweight checkout")
+
+    def test_switch_when_pending_merges(self):
+        """Test graceful failure if pending merges are outstanding."""
+        # Create 2 branches and a checkout
+        tree = self._setup_tree()
+        tree2 = tree.bzrdir.sprout('branch-2').open_workingtree()
+        checkout = tree.branch.create_checkout('checkout', lightweight=True)
+        # Change tree2 and merge it into the checkout without committing
+        self.build_tree(['branch-2/file-2'])
+        tree2.add('file-2')
+        tree2.commit('rev2')
+        checkout.merge_from_branch(tree2.branch)
+        # Check the error reporting is as expected
+        err = self.assertRaises(errors.BzrCommandError,
+            switch.switch, checkout.bzrdir, tree2.branch)
+        self.assertContainsRe(str(err),
+            "Pending merges must be committed or reverted before using switch")

=== modified file 'NEWS'
--- a/NEWS	2007-11-22 20:17:22 +0000
+++ b/NEWS	2007-11-23 00:19:02 +0000
@@ -25,6 +25,11 @@
    * New rich-root format, recording the same data about tree roots that's
      recorded for all other directories.  (Aaron Bentley)
 
+   * ``switch`` command added for changing the branch a lightweight checkout
+     is associated with and updating the tree to reflect the latest content
+     accordingly. This command was previously part of the BzrTools plug-in.
+     (Ian Clatworthy, Aaron Bentley, David Allouche)
+
   PERFORMANCE:
 
    * Commit updates the state of the working tree via a delta rather than

=== modified file 'bzrlib/builtins.py'
--- a/bzrlib/builtins.py	2007-11-22 02:34:39 +0000
+++ b/bzrlib/builtins.py	2007-11-23 00:19:02 +0000
@@ -4324,6 +4324,21 @@
         reconfiguration.apply(force)
 
 
+class cmd_switch(Command):
+    """Set the branch of a lightweight checkout and update."""
+
+    takes_args = ['to_location']
+
+    def run(self, to_location):
+        from bzrlib import switch
+        to_branch = Branch.open(to_location)
+        tree_location = '.'
+        control_dir = bzrdir.BzrDir.open_containing(tree_location)[0]
+        switch.switch(control_dir, to_branch)
+        note('Switched to branch: %s',
+            urlutils.unescape_for_display(to_branch.base, 'utf-8'))
+
+
 def _create_prefix(cur_transport):
     needed = [cur_transport]
     # Recurse upwards until we can create a directory successfully

=== modified file 'bzrlib/revision.py'
--- a/bzrlib/revision.py	2007-08-28 06:43:19 +0000
+++ b/bzrlib/revision.py	2007-11-21 15:10:44 +0000
@@ -452,7 +452,7 @@
 
 
 def ensure_null(revision_id):
-    """Ensure only NULL_REVISION is used to represent the null revisionn"""
+    """Ensure only NULL_REVISION is used to represent the null revision"""
     if revision_id is None:
         symbol_versioning.warn('NULL_REVISION should be used for the null'
             ' revision instead of None, as of bzr 0.91.',

=== modified file 'bzrlib/tests/__init__.py'
--- a/bzrlib/tests/__init__.py	2007-11-17 17:57:43 +0000
+++ b/bzrlib/tests/__init__.py	2007-11-23 00:19:02 +0000
@@ -2474,6 +2474,7 @@
                    'bzrlib.tests.test_store',
                    'bzrlib.tests.test_strace',
                    'bzrlib.tests.test_subsume',
+                   'bzrlib.tests.test_switch',
                    'bzrlib.tests.test_symbol_versioning',
                    'bzrlib.tests.test_tag',
                    'bzrlib.tests.test_testament',

=== modified file 'bzrlib/tests/blackbox/__init__.py'
--- a/bzrlib/tests/blackbox/__init__.py	2007-10-24 05:47:39 +0000
+++ b/bzrlib/tests/blackbox/__init__.py	2007-11-21 15:10:44 +0000
@@ -101,6 +101,7 @@
                      'bzrlib.tests.blackbox.test_sign_my_commits',
                      'bzrlib.tests.blackbox.test_split',
                      'bzrlib.tests.blackbox.test_status',
+                     'bzrlib.tests.blackbox.test_switch',
                      'bzrlib.tests.blackbox.test_tags',
                      'bzrlib.tests.blackbox.test_testament',
                      'bzrlib.tests.blackbox.test_too_much',




More information about the bazaar-commits mailing list