mercurial/hgweb.py
changeset 2113 633d733e7b11
parent 2103 caccf539c9a4
child 2119 f62195054c5b
equal deleted inserted replaced
2112:2b03c6733efa 2113:633d733e7b11
     8 
     8 
     9 import os, cgi, sys
     9 import os, cgi, sys
    10 import mimetypes
    10 import mimetypes
    11 from demandload import demandload
    11 from demandload import demandload
    12 demandload(globals(), "mdiff time re socket zlib errno ui hg ConfigParser")
    12 demandload(globals(), "mdiff time re socket zlib errno ui hg ConfigParser")
    13 demandload(globals(), "zipfile tempfile StringIO tarfile BaseHTTPServer util")
    13 demandload(globals(), "tempfile StringIO BaseHTTPServer util")
    14 demandload(globals(), "mimetypes templater")
    14 demandload(globals(), "archival mimetypes templater")
    15 from node import *
    15 from node import *
    16 from i18n import gettext as _
    16 from i18n import gettext as _
    17 
    17 
    18 def up(p):
    18 def up(p):
    19     if p[0] != "/":
    19     if p[0] != "/":
   680                      rev=self.repo.changelog.rev(n),
   680                      rev=self.repo.changelog.rev(n),
   681                      parent=self.siblings(cl.parents(n), cl.rev),
   681                      parent=self.siblings(cl.parents(n), cl.rev),
   682                      child=self.siblings(cl.children(n), cl.rev),
   682                      child=self.siblings(cl.children(n), cl.rev),
   683                      diff=diff)
   683                      diff=diff)
   684 
   684 
       
   685     archive_specs = {
       
   686         'bz2': ('application/x-tar', 'tbz2', '.tar.bz2', 'x-bzip2'),
       
   687         'gz': ('application/x-tar', 'tgz', '.tar.gz', 'x-gzip'),
       
   688         'zip': ('application/zip', 'zip', '.zip', None),
       
   689         }
       
   690 
   685     def archive(self, req, cnode, type):
   691     def archive(self, req, cnode, type):
   686         cs = self.repo.changelog.read(cnode)
   692         reponame = re.sub(r"\W+", "-", os.path.basename(self.reponame))
   687         mnode = cs[0]
   693         name = "%s-%s" % (reponame, short(cnode))
   688         mf = self.repo.manifest.read(mnode)
   694         mimetype, artype, extension, encoding = self.archive_specs[type]
   689         rev = self.repo.manifest.rev(mnode)
   695         headers = [('Content-type', mimetype),
   690         reponame = re.sub(r"\W+", "-", self.reponame)
   696                    ('Content-disposition', 'attachment; filename=%s%s' %
   691         name = "%s-%s/" % (reponame, short(cnode))
   697                     (name, extension))]
   692 
   698         if encoding:
   693         files = mf.keys()
   699             headers.append(('Content-encoding', encoding))
   694         files.sort()
   700         req.header(headers)
   695 
   701         archival.archive(self.repo, req.out, cnode, artype, prefix=name)
   696         if type == 'zip':
       
   697             tmp = tempfile.mkstemp()[1]
       
   698             try:
       
   699                 zf = zipfile.ZipFile(tmp, "w", zipfile.ZIP_DEFLATED)
       
   700 
       
   701                 for f in files:
       
   702                     zf.writestr(name + f, self.repo.file(f).read(mf[f]))
       
   703                 zf.close()
       
   704 
       
   705                 f = open(tmp, 'r')
       
   706                 req.httphdr('application/zip', name[:-1] + '.zip',
       
   707                         os.path.getsize(tmp))
       
   708                 req.write(f.read())
       
   709                 f.close()
       
   710             finally:
       
   711                 os.unlink(tmp)
       
   712 
       
   713         else:
       
   714             tf = tarfile.TarFile.open(mode='w|' + type, fileobj=req.out)
       
   715             mff = self.repo.manifest.readflags(mnode)
       
   716             mtime = int(time.time())
       
   717 
       
   718             if type == "gz":
       
   719                 encoding = "gzip"
       
   720             else:
       
   721                 encoding = "x-bzip2"
       
   722             req.header([('Content-type', 'application/x-tar'),
       
   723                     ('Content-disposition', 'attachment; filename=%s%s%s' %
       
   724                         (name[:-1], '.tar.', type)),
       
   725                     ('Content-encoding', encoding)])
       
   726             for fname in files:
       
   727                 rcont = self.repo.file(fname).read(mf[fname])
       
   728                 finfo = tarfile.TarInfo(name + fname)
       
   729                 finfo.mtime = mtime
       
   730                 finfo.size = len(rcont)
       
   731                 finfo.mode = mff[fname] and 0755 or 0644
       
   732                 tf.addfile(finfo, StringIO.StringIO(rcont))
       
   733             tf.close()
       
   734 
   702 
   735     # add tags to things
   703     # add tags to things
   736     # tags -> list of changesets corresponding to tags
   704     # tags -> list of changesets corresponding to tags
   737     # find tag, changeset, file
   705     # find tag, changeset, file
   738 
   706