Merge lp:~mbp/bzr/135234-checkout-relpath into lp:bzr

Proposed by Martin Pool
Status: Rejected
Rejected by: Martin Pool
Proposed branch: lp:~mbp/bzr/135234-checkout-relpath
Merge into: lp:bzr
Diff against target: 195 lines (+53/-18)
6 files modified
NEWS (+7/-3)
bzrlib/branch.py (+23/-7)
bzrlib/builtins.py (+2/-1)
bzrlib/tests/blackbox/test_bound_branches.py (+2/-0)
bzrlib/tests/blackbox/test_checkout.py (+12/-4)
bzrlib/tests/test_branch.py (+7/-3)
To merge this branch: bzr merge lp:~mbp/bzr/135234-checkout-relpath
Reviewer Review Type Date Requested Status
Ian Clatworthy Approve
Review via email: mp+21343@code.launchpad.net

Commit message

(mbp) store a relative URL to the master branch of checkouts

Description of the change

This fixes bug 135234 by:

- storing relative URLs to the master branch for lightweight and heavyweight checkouts
- coping with a trailing newline in the location file, in case it's manually edited

To post a comment you must log in.
Revision history for this message
Ian Clatworthy (ian-clatworthy) wrote :

3 cheers for this patch! Some minor things:

* there's a bit of junk in NEWS - "* Cope"
* builtins.py has ", e" added to an except clause and the exception isn't used anywhere. (I'm fine with leaving that as is though - it's harmless.)

review: Approve
lp:~mbp/bzr/135234-checkout-relpath updated
5094. By Martin Pool

Fix typo

Revision history for this message
Martin Pool (mbp) wrote :
lp:~mbp/bzr/135234-checkout-relpath updated
5095. By Martin Pool

merge news

Revision history for this message
Martin Pool (mbp) wrote :
Revision history for this message
Martin Pool (mbp) wrote :

fails in an info test:

 File "/home/pqm/bzr-pqm-workdir/home/+trunk/bzrlib/tests/blackbox/test_info.py", line 1210, in assertCheckoutStatusOutput
   ), out)
AssertionError: texts not equal:
 Lightweight checkout (format: 2a)
 Location:
   light checkout root: tree/lightcheckout
         checkout root: tree/checkout
- checkout of branch: repo/branch
+ checkout of branch: ../../repo/branch/
? ++++++ +

 Format:

Revision history for this message
Martin Pool (mbp) wrote :

Aaron raises a question in https://bugs.edge.launchpad.net/bzr/+bug/135234/comments/4 as to whether it's really ideal to store relative paths all the time.

We do as a general principle store relative paths when possible, partly because they're more likely to work when the same directories are addressed across different transports.

Revision history for this message
Ian Clatworthy (ian-clatworthy) wrote :

I think the frequency of relative paths is increasing as more people use Neil's colo plugin and the various workspace models in Explorer. We could detect those cases pretty easily I suspect, e.g. we want relative paths in at least these cases:

1. If the branch path starts with the checkout path
2. If the checkout path starts with the repository path.

Unmerged revisions

5095. By Martin Pool

merge news

5094. By Martin Pool

Fix typo

5093. By Martin Pool

Cope with a trailing newline in a .bzr/branch/location file

5092. By Martin Pool

Update BranchReference tests to expect relative URLs

5091. By Martin Pool

Branch references (used for lightweight checkouts) also store a relative url.

5090. By Martin Pool

The master of a bound branch is now stored as a relative URL if possible.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'NEWS'
--- NEWS 2010-03-22 13:59:33 +0000
+++ NEWS 2010-03-24 06:42:27 +0000
@@ -107,6 +107,9 @@
107 revspec as representing the first revision of the branch.107 revspec as representing the first revision of the branch.
108 (Vincent Ladeuil, #519862)108 (Vincent Ladeuil, #519862)
109109
110* ``bzr mkdir DIR`` will not create DIR unless DIR's parent is a versioned
111 directory. (Parth Malwankar, #138600)
112
110* ``bzr remove-tree`` can now remove multiple working trees.113* ``bzr remove-tree`` can now remove multiple working trees.
111 (Jared Hance, Andrew Bennetts, #253137)114 (Jared Hance, Andrew Bennetts, #253137)
112115
@@ -138,13 +141,14 @@
138 to the Ubuntu Units Policy <https://wiki.ubuntu.com/UnitsPolicy>.141 to the Ubuntu Units Policy <https://wiki.ubuntu.com/UnitsPolicy>.
139 (Gordon Tyler, #514399)142 (Gordon Tyler, #514399)
140143
144* The master of a bound branch is now stored as a relative URL if
145 possible, and similarly for lightweight checkouts.
146 (Martin Pool, #135234)
147
141* Support kind markers for socket and fifo filesystem objects. This148* Support kind markers for socket and fifo filesystem objects. This
142 prevents ``bzr status --short`` from crashing when those files are149 prevents ``bzr status --short`` from crashing when those files are
143 present. (John Arbash Meinel, #303275)150 present. (John Arbash Meinel, #303275)
144151
145* ``bzr mkdir DIR`` will not create DIR unless DIR's parent is a versioned
146 directory. (Parth Malwankar, #138600)
147
148* SSH child processes will now ignore SIGQUIT on nix systems so breaking into152* SSH child processes will now ignore SIGQUIT on nix systems so breaking into
149 the debugger won't kill the session.153 the debugger won't kill the session.
150 (Martin <gzlist@googlemail.com>, #162502)154 (Martin <gzlist@googlemail.com>, #162502)
151155
=== modified file 'bzrlib/branch.py'
--- bzrlib/branch.py 2010-03-22 13:59:33 +0000
+++ bzrlib/branch.py 2010-03-24 06:42:27 +0000
@@ -2004,7 +2004,8 @@
2004 def get_reference(self, a_bzrdir):2004 def get_reference(self, a_bzrdir):
2005 """See BranchFormat.get_reference()."""2005 """See BranchFormat.get_reference()."""
2006 transport = a_bzrdir.get_branch_transport(None)2006 transport = a_bzrdir.get_branch_transport(None)
2007 return transport.get_bytes('location')2007 # ignore trailing newline
2008 return transport.get_bytes('location').rstrip()
20082009
2009 def set_reference(self, a_bzrdir, to_branch):2010 def set_reference(self, a_bzrdir, to_branch):
2010 """See BranchFormat.set_reference()."""2011 """See BranchFormat.set_reference()."""
@@ -2019,12 +2020,17 @@
2019 raise errors.UninitializableFormat(self)2020 raise errors.UninitializableFormat(self)
2020 mutter('creating branch reference in %s', a_bzrdir.transport.base)2021 mutter('creating branch reference in %s', a_bzrdir.transport.base)
2021 branch_transport = a_bzrdir.get_branch_transport(self, name=name)2022 branch_transport = a_bzrdir.get_branch_transport(self, name=name)
2023 # NB: Don't add a trailing newline, because bzr prior to 2.2
2024 # can't cope with it
2022 branch_transport.put_bytes('location',2025 branch_transport.put_bytes('location',
2023 target_branch.bzrdir.root_transport.base)2026 urlutils.relative_url(a_bzrdir.root_transport.base,
2027 target_branch.base))
2024 branch_transport.put_bytes('format', self.get_format_string())2028 branch_transport.put_bytes('format', self.get_format_string())
2025 return self.open(2029 return self.open(
2026 a_bzrdir, name, _found=True,2030 a_bzrdir, name, _found=True,
2027 possible_transports=[target_branch.bzrdir.root_transport])2031 possible_transports=[a_bzrdir.root_transport,
2032 branch_transport,
2033 target_branch.bzrdir.root_transport])
20282034
2029 def __init__(self):2035 def __init__(self):
2030 super(BranchReferenceFormat, self).__init__()2036 super(BranchReferenceFormat, self).__init__()
@@ -2064,8 +2070,9 @@
2064 (format, self))2070 (format, self))
2065 if location is None:2071 if location is None:
2066 location = self.get_reference(a_bzrdir)2072 location = self.get_reference(a_bzrdir)
2073 abs_location = urlutils.join(a_bzrdir.root_transport.base, location)
2067 real_bzrdir = bzrdir.BzrDir.open(2074 real_bzrdir = bzrdir.BzrDir.open(
2068 location, possible_transports=possible_transports)2075 abs_location, possible_transports=possible_transports)
2069 result = real_bzrdir.open_branch(name=name, 2076 result = real_bzrdir.open_branch(name=name,
2070 ignore_fallbacks=ignore_fallbacks)2077 ignore_fallbacks=ignore_fallbacks)
2071 # this changes the behaviour of result.clone to create a new reference2078 # this changes the behaviour of result.clone to create a new reference
@@ -2412,8 +2419,14 @@
2412 if not bound_loc:2419 if not bound_loc:
2413 return None2420 return None
2414 try:2421 try:
2415 return Branch.open(bound_loc,2422 # if relative, interpret relative to my location
2416 possible_transports=possible_transports)2423 abs_bound_loc = urlutils.join(self.base, bound_loc)
2424 if possible_transports is None:
2425 possible_transports = []
2426 if self._transport not in possible_transports:
2427 possible_transports += [self._transport]
2428 return Branch.open(abs_bound_loc,
2429 possible_transports=possible_transports)
2417 except (errors.NotBranchError, errors.ConnectionError), e:2430 except (errors.NotBranchError, errors.ConnectionError), e:
2418 raise errors.BoundBranchConnectionFailure(2431 raise errors.BoundBranchConnectionFailure(
2419 self, bound_loc, e)2432 self, bound_loc, e)
@@ -2458,7 +2471,10 @@
2458 # last_rev is not in the other_last_rev history, AND2471 # last_rev is not in the other_last_rev history, AND
2459 # other_last_rev is not in our history, and do it without pulling2472 # other_last_rev is not in our history, and do it without pulling
2460 # history around2473 # history around
2461 self.set_bound_location(other.base)2474
2475 # If possible, use a relative URL so that things will work if the
2476 # whole thing is moved, or accessed across a different transport.
2477 self.set_bound_location(urlutils.relative_url(self.base, other.base))
24622478
2463 @needs_write_lock2479 @needs_write_lock
2464 def unbind(self):2480 def unbind(self):
24652481
=== modified file 'bzrlib/builtins.py'
--- bzrlib/builtins.py 2010-03-22 13:59:33 +0000
+++ bzrlib/builtins.py 2010-03-24 06:42:27 +0000
@@ -4652,10 +4652,11 @@
4652 else:4652 else:
4653 raise errors.BzrCommandError('No location supplied '4653 raise errors.BzrCommandError('No location supplied '
4654 'and no previous location known')4654 'and no previous location known')
4655 # open to check the other one actually exists
4655 b_other = Branch.open(location)4656 b_other = Branch.open(location)
4656 try:4657 try:
4657 b.bind(b_other)4658 b.bind(b_other)
4658 except errors.DivergedBranches:4659 except errors.DivergedBranches, e:
4659 raise errors.BzrCommandError('These branches have diverged.'4660 raise errors.BzrCommandError('These branches have diverged.'
4660 ' Try merging, and then bind again.')4661 ' Try merging, and then bind again.')
4661 if b.get_config().has_explicit_nickname():4662 if b.get_config().has_explicit_nickname():
46624663
=== modified file 'bzrlib/tests/blackbox/test_bound_branches.py'
--- bzrlib/tests/blackbox/test_bound_branches.py 2010-02-04 16:06:36 +0000
+++ bzrlib/tests/blackbox/test_bound_branches.py 2010-03-24 06:42:27 +0000
@@ -99,6 +99,8 @@
9999
100 d = BzrDir.open('')100 d = BzrDir.open('')
101 self.assertNotEqual(None, d.open_branch().get_master_branch())101 self.assertNotEqual(None, d.open_branch().get_master_branch())
102 # the relative URL is remembered: bug 135234
103 self.assertEqual("../base/", d.open_branch().get_bound_location())
102104
103 self.run_bzr('unbind')105 self.run_bzr('unbind')
104 self.assertEqual(None, d.open_branch().get_master_branch())106 self.assertEqual(None, d.open_branch().get_master_branch())
105107
=== modified file 'bzrlib/tests/blackbox/test_checkout.py'
--- bzrlib/tests/blackbox/test_checkout.py 2010-02-17 17:11:16 +0000
+++ bzrlib/tests/blackbox/test_checkout.py 2010-03-24 06:42:27 +0000
@@ -52,16 +52,24 @@
52 # if we have a checkout, the branch base should be 'branch'52 # if we have a checkout, the branch base should be 'branch'
53 source = bzrdir.BzrDir.open('branch')53 source = bzrdir.BzrDir.open('branch')
54 result = bzrdir.BzrDir.open('checkout')54 result = bzrdir.BzrDir.open('checkout')
55 self.assertEqual(source.open_branch().bzrdir.root_transport.base,55 # the bound location should normally be given relative to the checkout
56 result.open_branch().get_bound_location())56 # <https://launchpad.net/bugs/135234>
57 self.assertEqual("../branch/",
58 result.open_branch().get_bound_location())
5759
58 def test_checkout_light_makes_checkout(self):60 def test_checkout_light_makes_checkout(self):
59 self.run_bzr('checkout --lightweight branch checkout')61 self.run_bzr('checkout --lightweight branch checkout')
60 # if we have a checkout, the branch base should be 'branch'62 # if we have a checkout, the branch base should be 'branch'
61 source = bzrdir.BzrDir.open('branch')63 source = bzrdir.BzrDir.open('branch')
62 result = bzrdir.BzrDir.open('checkout')64 result = bzrdir.BzrDir.open('checkout')
63 self.assertEqual(source.open_branch().bzrdir.root_transport.base,65 # the bound location should normally be given relative to the checkout
64 result.open_branch().bzrdir.root_transport.base)66 # <https://launchpad.net/bugs/135234>
67 self.assertEqual("../branch/",
68 result.get_branch_reference())
69 # the same branch is actually opened
70 self.assertEqual(
71 source.open_branch().bzrdir.root_transport.base,
72 result.open_branch().bzrdir.root_transport.base)
6573
66 def test_checkout_dash_r(self):74 def test_checkout_dash_r(self):
67 self.run_bzr('checkout -r -2 branch checkout')75 self.run_bzr('checkout -r -2 branch checkout')
6876
=== modified file 'bzrlib/tests/test_branch.py'
--- bzrlib/tests/test_branch.py 2010-03-11 13:14:37 +0000
+++ bzrlib/tests/test_branch.py 2010-03-24 06:42:27 +0000
@@ -444,15 +444,19 @@
444 self.assertEqual(opened_branch.base, target_branch.base)444 self.assertEqual(opened_branch.base, target_branch.base)
445445
446 def test_get_reference(self):446 def test_get_reference(self):
447 """For a BranchReference, get_reference should reutrn the location."""447 """For a BranchReference, get_reference should return the location."""
448 branch = self.make_branch('target')448 branch = self.make_branch('target')
449 checkout = branch.create_checkout('checkout', lightweight=True)449 checkout = branch.create_checkout('checkout', lightweight=True)
450 reference_url = branch.bzrdir.root_transport.abspath('') + '/'450 reference_url = branch.bzrdir.root_transport.abspath('') + '/'
451 # if the api for create_checkout changes to return different checkout types451 # if the api for create_checkout changes to return different checkout types
452 # then this file read will fail.452 # then this file read will fail.
453 self.assertFileEqual(reference_url, 'checkout/.bzr/branch/location')453 self.assertFileEqual('../target/', 'checkout/.bzr/branch/location')
454 self.assertEqual(reference_url,454 self.assertEqual('../target/',
455 _mod_branch.BranchReferenceFormat().get_reference(checkout.bzrdir))455 _mod_branch.BranchReferenceFormat().get_reference(checkout.bzrdir))
456 # can cope with a trailing newline
457 self.build_tree_contents([('checkout/.bzr/branch/location', '../foo/\n')])
458 self.assertEqual('../foo/',
459 checkout.bzrdir.get_branch_reference())
456460
457461
458class TestHooks(tests.TestCase):462class TestHooks(tests.TestCase):