示例#1
0
文件: git.py 项目: lukaszb/vcs
    def fill_archive(self, stream=None, kind='tgz', prefix=None):
        """
        Fills up given stream.

        :param stream: file like object.
        :param kind: one of following: ``zip``, ``tgz`` or ``tbz2``.
            Default: ``tgz``.
        :param prefix: name of root directory in archive.
            Default is repository name and changeset's raw_id joined with dash
            (``repo-tip.<KIND>``).

        :raise ImproperArchiveTypeError: If given kind is wrong.
        :raise VcsError: If given stream is None

        """
        allowed_kinds = ARCHIVE_SPECS.keys()
        if kind not in allowed_kinds:
            raise ImproperArchiveTypeError('Archive kind not supported use one'
                'of %s', allowed_kinds)

        if prefix is None:
            prefix = '%s-%s' % (self.repository.name, self.short_id)
        elif prefix.startswith('/'):
            raise VCSError("Prefix cannot start with leading slash")
        elif prefix.strip() == '':
            raise VCSError("Prefix cannot be empty")

        if kind == 'zip':
            frmt = 'zip'
        else:
            frmt = 'tar'
        cmd = 'git archive --format=%s --prefix=%s/ %s' % (frmt, prefix,
            self.raw_id)
        if kind == 'tgz':
            cmd += ' | gzip -9'
        elif kind == 'tbz2':
            cmd += ' | bzip2 -9'

        if stream is None:
            raise VCSError('You need to pass in a valid stream for filling'
                           ' with archival data')
        else:
            arch_path = None

        popen = Popen(cmd, stdout=PIPE, stderr=PIPE, shell=True,
            cwd=self.repository.path)

        buffer_size = 1024 * 8
        chunk = popen.stdout.read(buffer_size)
        while chunk:
            stream.write(chunk)
            chunk = popen.stdout.read(buffer_size)
        # Make sure all descriptors would be read
        popen.communicate()
示例#2
0
    def archivefile(self, repo_name, fname):

        fileformat = None
        revision = None
        ext = None
        subrepos = request.GET.get('subrepos') == 'true'

        for a_type, ext_data in ARCHIVE_SPECS.items():
            archive_spec = fname.split(ext_data[1])
            if len(archive_spec) == 2 and archive_spec[1] == '':
                fileformat = a_type or ext_data[1]
                revision = archive_spec[0]
                ext = ext_data[1]

        try:
            dbrepo = RepoModel().get_by_repo_name(repo_name)
            if dbrepo.enable_downloads is False:
                return _('downloads disabled')

            cs = c.rhodecode_repo.get_changeset(revision)
            content_type = ARCHIVE_SPECS[fileformat][0]
        except ChangesetDoesNotExistError:
            return _('Unknown revision %s') % revision
        except EmptyRepositoryError:
            return _('Empty repository')
        except (ImproperArchiveTypeError, KeyError):
            return _('Unknown archive type')

        response.content_type = content_type
        response.content_disposition = 'attachment; filename=%s-%s%s' \
            % (repo_name, revision, ext)

        import tempfile
        archive = tempfile.mkstemp()[1]
        t = open(archive, 'wb')
        cs.fill_archive(stream=t, kind=fileformat, subrepos=subrepos)

        def get_chunked_archive(archive):
            stream = open(archive, 'rb')
            while True:
                data = stream.read(4096)
                if not data:
                    os.remove(archive)
                    break
                yield data

        return get_chunked_archive(archive)
示例#3
0
文件: hg.py 项目: lukaszb/vcs
    def fill_archive(self, stream=None, kind="tgz", prefix=None):
        """
        Fills up given stream.

        :param stream: file like object.
        :param kind: one of following: ``zip``, ``tgz`` or ``tbz2``.
            Default: ``tgz``.
        :param prefix: name of root directory in archive.
            Default is repository name and changeset's raw_id joined with dash
            (``repo-tip.<KIND>``).

        :raise ImproperArchiveTypeError: If given kind is wrong.
        :raise VcsError: If given stream is None
        """

        allowed_kinds = ARCHIVE_SPECS.keys()
        if kind not in allowed_kinds:
            raise ImproperArchiveTypeError("Archive kind not supported use one" "of %s", allowed_kinds)

        if stream is None:
            raise VCSError("You need to pass in a valid stream for filling" " with archival data")

        if prefix is None:
            prefix = "%s-%s" % (self.repository.name, self.short_id)
        elif prefix.startswith("/"):
            raise VCSError("Prefix cannot start with leading slash")
        elif prefix.strip() == "":
            raise VCSError("Prefix cannot be empty")

        archival.archive(self.repository._repo, stream, self.raw_id, kind, prefix=prefix)

        # stream.close()

        if stream.closed and hasattr(stream, "name"):
            stream = open(stream.name, "rb")
        elif hasattr(stream, "mode") and "r" not in stream.mode:
            stream = open(stream.name, "rb")
        else:
            stream.seek(0)