subrepo: abort instead of pushing/pulling to the repo itself
_abssource will now abort (or return None) in the rare cases where no push/pull
path can be found.
--- a/mercurial/subrepo.py Tue Oct 19 03:55:28 2010 +0200
+++ b/mercurial/subrepo.py Tue Oct 19 03:56:20 2010 +0200
@@ -167,26 +167,33 @@
return sub._path
return reporelpath(sub._repo)
-def _abssource(repo, push=False):
- """return pull/push path of repo - either based on parent repo
- .hgsub info or on the subrepos own config"""
+def _abssource(repo, push=False, abort=True):
+ """return pull/push path of repo - either based on parent repo .hgsub info
+ or on the top repo config. Abort or return None if no source found."""
if hasattr(repo, '_subparent'):
source = repo._subsource
if source.startswith('/') or '://' in source:
return source
- parent = _abssource(repo._subparent, push)
- if '://' in parent:
- if parent[-1] == '/':
- parent = parent[:-1]
- r = urlparse.urlparse(parent + '/' + source)
- r = urlparse.urlunparse((r[0], r[1],
- posixpath.normpath(r[2]),
- r[3], r[4], r[5]))
- return r
- return posixpath.normpath(os.path.join(parent, repo._subsource))
- if push and repo.ui.config('paths', 'default-push'):
- return repo.ui.config('paths', 'default-push', repo.root)
- return repo.ui.config('paths', 'default', repo.root)
+ parent = _abssource(repo._subparent, push, abort=False)
+ if parent:
+ if '://' in parent:
+ if parent[-1] == '/':
+ parent = parent[:-1]
+ r = urlparse.urlparse(parent + '/' + source)
+ r = urlparse.urlunparse((r[0], r[1],
+ posixpath.normpath(r[2]),
+ r[3], r[4], r[5]))
+ return r
+ else: # plain file system path
+ return posixpath.normpath(os.path.join(parent, repo._subsource))
+ else: # recursion reached top repo
+ if push and repo.ui.config('paths', 'default-push'):
+ return repo.ui.config('paths', 'default-push')
+ if repo.ui.config('paths', 'default'):
+ return repo.ui.config('paths', 'default')
+ if abort:
+ raise util.Abort(_("default path for subrepository %s not found") %
+ reporelpath(repo))
def itersubrepos(ctx1, ctx2):
"""find subrepos in ctx1 or ctx2"""
@@ -314,11 +321,12 @@
fp.write('[paths]\n')
def addpathconfig(key, value):
- fp.write('%s = %s\n' % (key, value))
- self._repo.ui.setconfig('paths', key, value)
+ if value:
+ fp.write('%s = %s\n' % (key, value))
+ self._repo.ui.setconfig('paths', key, value)
- defpath = _abssource(self._repo)
- defpushpath = _abssource(self._repo, True)
+ defpath = _abssource(self._repo, abort=False)
+ defpushpath = _abssource(self._repo, True, abort=False)
addpathconfig('default', defpath)
if defpath != defpushpath:
addpathconfig('default-push', defpushpath)
--- a/tests/test-subrepo.t Tue Oct 19 03:55:28 2010 +0200
+++ b/tests/test-subrepo.t Tue Oct 19 03:56:20 2010 +0200
@@ -585,3 +585,64 @@
$ hg -R repo update
0 files updated, 0 files merged, 0 files removed, 0 files unresolved
$ rm -rf repo2 repo
+
+
+Issue1852 subrepos with relative paths always push/pull relative to default
+
+Prepare a repo with subrepo
+
+ $ hg init issue1852a
+ $ cd issue1852a
+ $ hg init sub/repo
+ $ echo test > sub/repo/foo
+ $ hg -R sub/repo add sub/repo/foo
+ $ echo sub/repo = sub/repo > .hgsub
+ $ hg add .hgsub
+ $ hg ci -mtest
+ committing subrepository sub/repo
+ $ echo test >> sub/repo/foo
+ $ hg ci -mtest
+ committing subrepository sub/repo
+ $ cd ..
+
+Create repo without default path, pull top repo, and see what happens on update
+
+ $ hg init issue1852b
+ $ hg -R issue1852b pull issue1852a
+ pulling from issue1852a
+ requesting all changes
+ adding changesets
+ adding manifests
+ adding file changes
+ added 2 changesets with 3 changes to 2 files
+ (run 'hg update' to get a working copy)
+ $ hg -R issue1852b update
+ abort: default path for subrepository sub/repo not found
+ [255]
+
+Pull -u now doesn't help
+
+ $ hg -R issue1852b pull -u issue1852a
+ pulling from issue1852a
+ searching for changes
+ no changes found
+
+Try the same, but with pull -u
+
+ $ hg init issue1852c
+ $ hg -R issue1852c pull -r0 -u issue1852a
+ pulling from issue1852a
+ requesting all changes
+ adding changesets
+ adding manifests
+ adding file changes
+ added 1 changesets with 2 changes to 2 files
+ abort: default path for subrepository sub/repo not found
+ [255]
+
+Try to push from the other side
+
+ $ hg -R issue1852a push issue1852c
+ pushing to issue1852c
+ abort: default path for subrepository sub/repo not found
+ [255]