#!/usr/bin/python ######################################################################## # Copyright (C) 2010 VMWare, Inc. # # All Rights Reserved # ######################################################################## import tarfile from .Utils import EsxGzip from .Utils.Misc import isString from . import Errors class PayloadTar(object): """Implements a representation of a gzipped tar which can be used to cache non-tardisk payloads for use by the installer. """ PAYLOADTAR_PREFIX = "var/db/payloads" def __init__(self, filepath): """Class constructor. Parameters: * filepath - Must be either a string, giving the path of a file to write the gzipp'ed tar output, or a file-like object where gzipp'ed tar output will be written. In either case, the file or file-like object must be writable. """ if isString(filepath): self.fobj = EsxGzip.GzipFile(filepath, "wb") else: self.fobj = EsxGzip.GzipFile(fileobj=filepath, mode="wb") self.tarfile = tarfile.open(fileobj=self.fobj, mode="w") def AddPayload(self, fobj, payload, payloadfn=None): if payloadfn is None: payloadfn = payload.name dirname = "/".join((self.PAYLOADTAR_PREFIX, payload.payloadtype)) self._AddDirectory(dirname) tarname = "/".join((dirname, payloadfn)) tarinfo = tarfile.TarInfo(tarname) tarinfo.mode = 0o644 tarinfo.size = payload.size self.tarfile.addfile(tarinfo, fobj) def _AddDirectory(self, directorypath): dirparts = directorypath.split("/") for i in range(len(dirparts)): dirname = "/".join(dirparts[:i+1]) if not dirname or dirname in self.tarfile.getnames(): continue tarinfo = tarfile.TarInfo(dirname) tarinfo.type = tarfile.DIRTYPE tarinfo.mode = 0o755 self.tarfile.addfile(tarinfo) def Close(self): self.tarfile.close() self.fobj.close() close = Close