##// END OF EJS Templates
make static-http work with empty repos (issue965)
Dirkjan Ochtman -
r6028:6605a03c default
parent child Browse files
Show More
@@ -1,78 +1,86 b''
1 1 # statichttprepo.py - simple http repository class for mercurial
2 2 #
3 3 # This provides read-only repo access to repositories exported via static http
4 4 #
5 5 # Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
6 6 #
7 7 # This software may be used and distributed according to the terms
8 8 # of the GNU General Public License, incorporated herein by reference.
9 9
10 10 from i18n import _
11 11 import changelog, filelog, httprangereader
12 import repo, localrepo, manifest, os, urllib, urllib2, util
12 import repo, localrepo, manifest, util
13 import urllib, urllib2, errno
13 14
14 15 class rangereader(httprangereader.httprangereader):
15 16 def read(self, size=None):
16 17 try:
17 18 return httprangereader.httprangereader.read(self, size)
18 19 except urllib2.HTTPError, inst:
19 raise IOError(None, inst)
20 num = inst.code == 404 and errno.ENOENT or None
21 raise IOError(num, inst)
20 22 except urllib2.URLError, inst:
21 23 raise IOError(None, inst.reason[1])
22 24
23 25 def opener(base):
24 26 """return a function that opens files over http"""
25 27 p = base
26 28 def o(path, mode="r"):
27 29 f = "/".join((p, urllib.quote(path)))
28 30 return rangereader(f)
29 31 return o
30 32
31 33 class statichttprepository(localrepo.localrepository):
32 34 def __init__(self, ui, path):
33 35 self._url = path
34 36 self.ui = ui
35 37
36 38 self.path = path.rstrip('/') + "/.hg"
37 39 self.opener = opener(self.path)
40
38 41 # find requirements
39 42 try:
40 43 requirements = self.opener("requires").read().splitlines()
41 except IOError:
44 except IOError, inst:
45 if inst.errno == errno.ENOENT:
46 msg = _("'%s' does not appear to be an hg repository") % path
47 raise repo.RepoError(msg)
48 else:
42 49 requirements = []
50
43 51 # check them
44 52 for r in requirements:
45 53 if r not in self.supported:
46 54 raise repo.RepoError(_("requirement '%s' not supported") % r)
47 55
48 56 # setup store
49 57 if "store" in requirements:
50 58 self.encodefn = util.encodefilename
51 59 self.decodefn = util.decodefilename
52 60 self.spath = self.path + "/store"
53 61 else:
54 62 self.encodefn = lambda x: x
55 63 self.decodefn = lambda x: x
56 64 self.spath = self.path
57 65 self.sopener = util.encodedopener(opener(self.spath), self.encodefn)
58 66
59 67 self.manifest = manifest.manifest(self.sopener)
60 68 self.changelog = changelog.changelog(self.sopener)
61 69 self.tagscache = None
62 70 self.nodetagscache = None
63 71 self.encodepats = None
64 72 self.decodepats = None
65 73
66 74 def url(self):
67 75 return 'static-' + self._url
68 76
69 77 def dev(self):
70 78 return -1
71 79
72 80 def local(self):
73 81 return False
74 82
75 83 def instance(ui, path, create):
76 84 if create:
77 85 raise util.Abort(_('cannot create new static-http repository'))
78 86 return statichttprepository(ui, path[7:])
@@ -1,66 +1,81 b''
1 1 #!/bin/sh
2 2
3 3 cp "$TESTDIR"/printenv.py .
4 4
5 5 http_proxy= hg clone static-http://localhost:$HGPORT/ copy
6 6 echo $?
7 7 test -d copy || echo copy: No such file or directory
8 8
9 9 # This server doesn't do range requests so it's basically only good for
10 10 # one pull
11 11 cat > dumb.py <<EOF
12 12 import BaseHTTPServer, SimpleHTTPServer, os, signal
13 13
14 14 def run(server_class=BaseHTTPServer.HTTPServer,
15 15 handler_class=SimpleHTTPServer.SimpleHTTPRequestHandler):
16 16 server_address = ('localhost', int(os.environ['HGPORT']))
17 17 httpd = server_class(server_address, handler_class)
18 18 httpd.serve_forever()
19 19
20 20 signal.signal(signal.SIGTERM, lambda x: sys.exit(0))
21 21 run()
22 22 EOF
23 23
24 24 python dumb.py 2>/dev/null &
25 25 echo $! >> $DAEMON_PIDS
26 26
27 27 mkdir remote
28 28 cd remote
29 29 hg init
30 30 echo foo > bar
31 31 hg add bar
32 32 hg commit -m"test" -d "1000000 0"
33 33 hg tip
34 34
35 35 cd ..
36 36
37 37 http_proxy= hg clone static-http://localhost:$HGPORT/remote local | sed -e 's,:[0-9][0-9]*/,/,'
38 38
39 39 cd local
40 40 hg verify
41 41 cat bar
42 42
43 43 cd ../remote
44 44 echo baz > quux
45 45 hg commit -A -mtest2 -d '100000000 0'
46 46
47 47 cd ../local
48 48 echo '[hooks]' >> .hg/hgrc
49 49 echo 'changegroup = python ../printenv.py changegroup' >> .hg/hgrc
50 50 http_proxy= hg pull | sed -e 's,:[0-9][0-9]*/,/,'
51 51
52 52 echo '% test with "/" URI (issue 747)'
53 53 cd ..
54 54 hg init
55 55 echo a > a
56 56 hg add a
57 57 hg ci -ma
58 58
59 59 http_proxy= hg clone static-http://localhost:$HGPORT/ local2 | sed -e 's,:[0-9][0-9]*/,/,'
60 60
61 61 cd local2
62 62 hg verify
63 63 cat a
64 64 hg paths | sed -e 's,:[0-9][0-9]*/,/,'
65 65
66 echo '% test with empty repo (issue965)'
67 cd ..
68 hg init remotempty
69
70 http_proxy= hg clone static-http://localhost:$HGPORT/remotempty local3 | sed -e 's,:[0-9][0-9]*/,/,'
71
72 cd local3
73 hg verify
74 hg paths | sed -e 's,:[0-9][0-9]*/,/,'
75
76 echo '% test with non-repo'
77 cd ..
78 mkdir notarepo
79 http_proxy= hg clone static-http://localhost:$HGPORT/notarepo local3 2>&1 | sed -e 's,:[0-9][0-9]*/,/,'
80
66 81 kill $!
@@ -1,44 +1,55 b''
1 1 abort: Connection refused
2 2 255
3 3 copy: No such file or directory
4 4 changeset: 0:53e17d176ae6
5 5 tag: tip
6 6 user: test
7 7 date: Mon Jan 12 13:46:40 1970 +0000
8 8 summary: test
9 9
10 10 requesting all changes
11 11 adding changesets
12 12 adding manifests
13 13 adding file changes
14 14 added 1 changesets with 1 changes to 1 files
15 15 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
16 16 checking changesets
17 17 checking manifests
18 18 crosschecking files in changesets and manifests
19 19 checking files
20 20 1 files, 1 changesets, 1 total revisions
21 21 foo
22 22 adding quux
23 23 changegroup hook: HG_NODE=34401e0e9971e9720b613d9089ffa9a6eefb3d2d HG_SOURCE=pull HG_URL=static-http://localhost/remote
24 24 pulling from static-http://localhost/remote
25 25 searching for changes
26 26 adding changesets
27 27 adding manifests
28 28 adding file changes
29 29 added 1 changesets with 1 changes to 1 files
30 30 (run 'hg update' to get a working copy)
31 31 % test with "/" URI (issue 747)
32 32 requesting all changes
33 33 adding changesets
34 34 adding manifests
35 35 adding file changes
36 36 added 1 changesets with 1 changes to 1 files
37 37 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
38 38 checking changesets
39 39 checking manifests
40 40 crosschecking files in changesets and manifests
41 41 checking files
42 42 1 files, 1 changesets, 1 total revisions
43 43 a
44 44 default = static-http://localhost/
45 % test with empty repo (issue965)
46 no changes found
47 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
48 checking changesets
49 checking manifests
50 crosschecking files in changesets and manifests
51 checking files
52 0 files, 0 changesets, 0 total revisions
53 default = static-http://localhost/remotempty
54 % test with non-repo
55 abort: 'http://localhost/notarepo' does not appear to be an hg repository!
General Comments 0
You need to be logged in to leave comments. Login now