mercurial/hgweb/hgweb_mod.py
changeset 4232 0d51eb296fb9
parent 4164 5c1e18bb804c
parent 4228 c52b7176af94
child 4250 ca639faa38a2
equal deleted inserted replaced
4224:2a8b6d78d7ee 4232:0d51eb296fb9
  1064         if not self.check_perm(req, 'push', False):
  1064         if not self.check_perm(req, 'push', False):
  1065             bail(_('push not authorized\n'),
  1065             bail(_('push not authorized\n'),
  1066                  headers={'status': '401 Unauthorized'})
  1066                  headers={'status': '401 Unauthorized'})
  1067             return
  1067             return
  1068 
  1068 
  1069         req.httphdr("application/mercurial-0.1")
       
  1070 
       
  1071         their_heads = req.form['heads'][0].split(' ')
  1069         their_heads = req.form['heads'][0].split(' ')
  1072 
  1070 
  1073         def check_heads():
  1071         def check_heads():
  1074             heads = map(hex, self.repo.heads())
  1072             heads = map(hex, self.repo.heads())
  1075             return their_heads == [hex('force')] or their_heads == heads
  1073             return their_heads == [hex('force')] or their_heads == heads
  1076 
  1074 
  1077         # fail early if possible
  1075         # fail early if possible
  1078         if not check_heads():
  1076         if not check_heads():
  1079             bail(_('unsynced changes\n'))
  1077             bail(_('unsynced changes\n'))
  1080             return
  1078             return
       
  1079 
       
  1080         req.httphdr("application/mercurial-0.1")
  1081 
  1081 
  1082         # do not lock repo until all changegroup data is
  1082         # do not lock repo until all changegroup data is
  1083         # streamed. save to temporary file.
  1083         # streamed. save to temporary file.
  1084 
  1084 
  1085         fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-')
  1085         fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-')
  1087         try:
  1087         try:
  1088             length = int(req.env['CONTENT_LENGTH'])
  1088             length = int(req.env['CONTENT_LENGTH'])
  1089             for s in util.filechunkiter(req, limit=length):
  1089             for s in util.filechunkiter(req, limit=length):
  1090                 fp.write(s)
  1090                 fp.write(s)
  1091 
  1091 
  1092             lock = self.repo.lock()
       
  1093             try:
  1092             try:
  1094                 if not check_heads():
  1093                 lock = self.repo.lock()
  1095                     req.write('0\n')
  1094                 try:
  1096                     req.write(_('unsynced changes\n'))
  1095                     if not check_heads():
  1097                     return
  1096                         req.write('0\n')
  1098 
  1097                         req.write(_('unsynced changes\n'))
  1099                 fp.seek(0)
  1098                         return
  1100                 header = fp.read(6)
  1099 
  1101                 if not header.startswith("HG"):
  1100                     fp.seek(0)
  1102                     # old client with uncompressed bundle
  1101                     header = fp.read(6)
  1103                     def generator(f):
  1102                     if not header.startswith("HG"):
  1104                         yield header
  1103                         # old client with uncompressed bundle
  1105                         for chunk in f:
  1104                         def generator(f):
  1106                             yield chunk
  1105                             yield header
  1107                 elif not header.startswith("HG10"):
  1106                             for chunk in f:
  1108                     req.write("0\n")
  1107                                 yield chunk
  1109                     req.write(_("unknown bundle version\n"))
  1108                     elif not header.startswith("HG10"):
  1110                     return
  1109                         req.write("0\n")
  1111                 elif header == "HG10GZ":
  1110                         req.write(_("unknown bundle version\n"))
  1112                     def generator(f):
  1111                         return
  1113                         zd = zlib.decompressobj()
  1112                     elif header == "HG10GZ":
  1114                         for chunk in f:
  1113                         def generator(f):
  1115                             yield zd.decompress(chunk)
  1114                             zd = zlib.decompressobj()
  1116                 elif header == "HG10BZ":
  1115                             for chunk in f:
  1117                     def generator(f):
  1116                                 yield zd.decompress(chunk)
  1118                         zd = bz2.BZ2Decompressor()
  1117                     elif header == "HG10BZ":
  1119                         zd.decompress("BZ")
  1118                         def generator(f):
  1120                         for chunk in f:
  1119                             zd = bz2.BZ2Decompressor()
  1121                             yield zd.decompress(chunk)
  1120                             zd.decompress("BZ")
  1122                 elif header == "HG10UN":
  1121                             for chunk in f:
  1123                     def generator(f):
  1122                                 yield zd.decompress(chunk)
  1124                         for chunk in f:
  1123                     elif header == "HG10UN":
  1125                             yield chunk
  1124                         def generator(f):
       
  1125                             for chunk in f:
       
  1126                                 yield chunk
       
  1127                     else:
       
  1128                         req.write("0\n")
       
  1129                         req.write(_("unknown bundle compression type\n"))
       
  1130                         return
       
  1131                     gen = generator(util.filechunkiter(fp, 4096))
       
  1132 
       
  1133                     # send addchangegroup output to client
       
  1134 
       
  1135                     old_stdout = sys.stdout
       
  1136                     sys.stdout = cStringIO.StringIO()
       
  1137 
       
  1138                     try:
       
  1139                         url = 'remote:%s:%s' % (proto,
       
  1140                                                 req.env.get('REMOTE_HOST', ''))
       
  1141                         try:
       
  1142                             ret = self.repo.addchangegroup(
       
  1143                                         util.chunkbuffer(gen), 'serve', url)
       
  1144                         except util.Abort, inst:
       
  1145                             sys.stdout.write("abort: %s\n" % inst)
       
  1146                             ret = 0
       
  1147                     finally:
       
  1148                         val = sys.stdout.getvalue()
       
  1149                         sys.stdout = old_stdout
       
  1150                     req.write('%d\n' % ret)
       
  1151                     req.write(val)
       
  1152                 finally:
       
  1153                     lock.release()
       
  1154             except (OSError, IOError), inst:
       
  1155                 req.write('0\n')
       
  1156                 filename = getattr(inst, 'filename', '')
       
  1157                 # Don't send our filesystem layout to the client
       
  1158                 if filename.startswith(self.repo.root):
       
  1159                     filename = filename[len(self.repo.root)+1:]
  1126                 else:
  1160                 else:
  1127                     req.write("0\n")
  1161                     filename = ''
  1128                     req.write(_("unknown bundle compression type\n"))
  1162                 error = getattr(inst, 'strerror', 'Unknown error')
  1129                     return
  1163                 req.write('%s: %s\n' % (error, filename))
  1130                 gen = generator(util.filechunkiter(fp, 4096))
       
  1131 
       
  1132                 # send addchangegroup output to client
       
  1133 
       
  1134                 old_stdout = sys.stdout
       
  1135                 sys.stdout = cStringIO.StringIO()
       
  1136 
       
  1137                 try:
       
  1138                     url = 'remote:%s:%s' % (proto,
       
  1139                                             req.env.get('REMOTE_HOST', ''))
       
  1140                     try:
       
  1141                         ret = self.repo.addchangegroup(util.chunkbuffer(gen),
       
  1142                                                        'serve', url)
       
  1143                     except util.Abort, inst:
       
  1144                         sys.stdout.write("abort: %s\n" % inst)
       
  1145                         ret = 0
       
  1146                 finally:
       
  1147                     val = sys.stdout.getvalue()
       
  1148                     sys.stdout = old_stdout
       
  1149                 req.write('%d\n' % ret)
       
  1150                 req.write(val)
       
  1151             finally:
       
  1152                 lock.release()
       
  1153         finally:
  1164         finally:
  1154             fp.close()
  1165             fp.close()
  1155             os.unlink(tempname)
  1166             os.unlink(tempname)
  1156 
  1167 
  1157     def do_stream_out(self, req):
  1168     def do_stream_out(self, req):