Kiln » Kiln Extensions
Clone URL:  
httpstore.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
'''HTTP-based store.''' import inspect import urlparse import urllib2 from mercurial import util, url as url_ from mercurial.i18n import _ try: from mercurial import httpconnection except ImportError: pass import bfutil, basestore class httpstore(basestore.basestore): """A store accessed via HTTP""" def __init__(self, ui, repo, url): url = bfutil.urljoin(url, 'bfile') super(httpstore, self).__init__(ui, repo, url) self.rawurl, self.path = urlparse.urlsplit(self.url)[1:3] try: # Mercurial >= 1.9 baseurl, authinfo = util.url(self.url).authinfo() except AttributeError: # Mercurial <= 1.8 baseurl, authinfo = url_.getauthinfo(self.url) self.opener = url_.opener(self.ui, authinfo) def put(self, source, hash): self.sendfile(source, hash) self.ui.debug('put %s to remote store\n' % source) def exists(self, hash): return self._verify(hash) def sendfile(self, filename, hash): if self._verify(hash): return self.ui.debug('httpstore.sendfile(%s, %s)\n' % (filename, hash)) try: # Mercurial >= 1.9 baseurl, authinfo = util.url(self.url).authinfo() except AttributeError: # Mercurial <= 1.8 baseurl, authinfo = url_.getauthinfo(self.url) fd = None try: try: # Mercurial >= 1.9 fd = httpconnection.httpsendfile(self.ui, filename, 'rb') except ImportError: if 'ui' in inspect.getargspec(url_.httpsendfile.__init__)[0]: # Mercurial == 1.8 fd = url_.httpsendfile(self.ui, filename, 'rb') else: # Mercurial <= 1.7 fd = url_.httpsendfile(filename, 'rb') request = urllib2.Request(bfutil.urljoin(baseurl, hash), fd) try: url = self.opener.open(request) self.ui.note(_('[OK] %s/%s\n') % (self.rawurl, url.geturl())) except urllib2.HTTPError, e: raise util.Abort(_('unable to POST: %s\n') % e.msg) except Exception, e: raise util.Abort(_('%s') % e) finally: if fd: fd.close() def _getfile(self, tmpfile, filename, hash): try: # Mercurial >= 1.9 baseurl, authinfo = util.url(self.url).authinfo() except AttributeError: # Mercurial <= 1.8 baseurl, authinfo = url_.getauthinfo(self.url) url = bfutil.urljoin(baseurl, hash) try: request = urllib2.Request(url) infile = self.opener.open(request) except urllib2.HTTPError, err: detail = _("HTTP error: %s %s") % (err.code, err.msg) raise basestore.StoreError(filename, hash, url, detail) except urllib2.URLError, err: # This usually indicates a connection problem, so don't # keep trying with the other files... they will probably # all fail too. reason = err[0][1] # assumes err[0] is a socket.error raise util.Abort('%s: %s' % (baseurl, reason)) return bfutil.copyandhash(bfutil.blockstream(infile), tmpfile) def _verify(self, hash): try: # Mercurial >= 1.9 baseurl, authinfo = util.url(self.url).authinfo() except AttributeError: # Mercurial <= 1.8 baseurl, authinfo = url_.getauthinfo(self.url) store_path = bfutil.urljoin(baseurl, hash) request = urllib2.Request(store_path) request.add_header('SHA1-Request', hash) try: url = self.opener.open(request) if 'Content-SHA1' in url.info() and hash == url.info()['Content-SHA1']: return True else: return False except: return False def _verifyfile(self, cctx, cset, contents, standin, verified): try: # Mercurial >= 1.9 baseurl, authinfo = util.url(self.url).authinfo() except AttributeError: # Mercurial <= 1.8 baseurl, authinfo = url_.getauthinfo(self.url) filename = bfutil.splitstandin(standin) if not filename: return False fctx = cctx[standin] key = (filename, fctx.filenode()) if key in verified: return False expect_hash = fctx.data()[0:40] store_path = bfutil.urljoin(baseurl, expect_hash) verified.add(key) request = urllib2.Request(store_path) request.add_header('SHA1-Request',expect_hash) try: url = self.opener.open(request) if 'Content-SHA1' in url.info(): rhash = url.info()['Content-SHA1'] if rhash == expect_hash: return False else: self.ui.warn( _('changeset %s: %s: contents differ\n (%s)\n') % (cset, filename, store_path)) return True # failed else: self.ui.warn(_('remote did not send a hash, ' 'it probably does not understand this protocol\n')) return False except urllib2.HTTPError, e: if e.code == 404: self.ui.warn( _('changeset %s: %s missing\n (%s)\n') % (cset, filename, store_path)) return True # failed else: raise util.Abort(_('check failed, unexpected response' 'status: %d: %s') % (e.code, e.msg))